summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohannes 'josch' Schauer <josch@debian.org>2020-02-22 18:04:35 +0100
committerJohannes 'josch' Schauer <josch@debian.org>2020-02-22 18:04:35 +0100
commit779ac0902d2586e1ac31ad41881d8922ec40a7ea (patch)
tree692cccf44eccc86c0b19e7d1e3baaca8e871c173
parent550e60ae0c7e181f945a5dd54bd5e0c85939890a (diff)
New upstream version 2019-12-01+dfsg1
-rw-r--r--README.md17
-rw-r--r--actions/ConnectivityAction.php136
-rw-r--r--actions/DisplayAction.php129
-rw-r--r--bridges/AmazonPriceTrackerBridge.php8
-rw-r--r--bridges/AppleAppStoreBridge.php149
-rw-r--r--bridges/AppleMusicBridge.php20
-rw-r--r--bridges/AtmoNouvelleAquitaineBridge.php2
-rw-r--r--bridges/BandcampBridge.php368
-rw-r--r--bridges/BastaBridge.php16
-rw-r--r--bridges/BingSearchBridge.php2
-rw-r--r--bridges/BloombergBridge.php69
-rw-r--r--bridges/CNETFranceBridge.php4
-rw-r--r--bridges/CachetBridge.php6
-rw-r--r--bridges/CastorusBridge.php2
-rw-r--r--bridges/CollegeDeFranceBridge.php2
-rw-r--r--bridges/ComicsKingdomBridge.php65
-rw-r--r--bridges/ContainerLinuxReleasesBridge.php18
-rw-r--r--bridges/DarkReadingBridge.php79
-rw-r--r--bridges/DesoutterBridge.php10
-rw-r--r--bridges/DiarioDoAlentejoBridge.php60
-rw-r--r--bridges/DownDetectorBridge.php6195
-rw-r--r--bridges/DribbbleBridge.php6
-rw-r--r--bridges/EconomistBridge.php2
-rw-r--r--bridges/ElloBridge.php4
-rw-r--r--bridges/ElsevierBridge.php2
-rw-r--r--bridges/EsquerdaNetBridge.php70
-rw-r--r--bridges/ExtremeDownloadBridge.php2
-rw-r--r--bridges/FB2Bridge.php39
-rw-r--r--bridges/FacebookBridge.php46
-rw-r--r--bridges/FreeCodeCampBridge.php27
-rw-r--r--bridges/FurAffinityUserBridge.php110
-rw-r--r--bridges/GQMagazineBridge.php2
-rw-r--r--bridges/GiphyBridge.php2
-rw-r--r--bridges/GoogleSearchBridge.php18
-rw-r--r--bridges/HDWallpapersBridge.php4
-rw-r--r--bridges/InstagramBridge.php163
-rw-r--r--bridges/JapanExpoBridge.php46
-rw-r--r--bridges/KonachanBridge.php2
-rw-r--r--bridges/KununuBridge.php10
-rw-r--r--bridges/LeBonCoinBridge.php8
-rw-r--r--bridges/ListverseBridge.php22
-rw-r--r--bridges/MangareaderBridge.php2
-rw-r--r--bridges/MediapartBridge.php49
-rw-r--r--bridges/N26Bridge.php10
-rw-r--r--bridges/NFLRUSBridge.php60
-rw-r--r--bridges/NiceMatinBridge.php2
-rw-r--r--bridges/NineGagBridge.php40
-rw-r--r--bridges/OpenwhydBridge.php (renamed from bridges/WhydBridge.php)15
-rw-r--r--bridges/ParuVenduImmoBridge.php2
-rw-r--r--bridges/PickyWallpapersBridge.php2
-rw-r--r--bridges/PikabuBridge.php9
-rw-r--r--bridges/PinterestBridge.php2
-rw-r--r--bridges/PlantUMLReleasesBridge.php67
-rw-r--r--bridges/ReadComicsBridge.php44
-rw-r--r--bridges/RedditBridge.php40
-rw-r--r--bridges/Releases3DSBridge.php36
-rw-r--r--bridges/ReporterreBridge.php2
-rw-r--r--bridges/RevolutBridge.php81
-rw-r--r--bridges/RoadAndTrackBridge.php2
-rw-r--r--bridges/Rule34Bridge.php2
-rw-r--r--bridges/Rule34pahealBridge.php2
-rw-r--r--bridges/SafebooruBridge.php2
-rw-r--r--bridges/ScmbBridge.php2
-rw-r--r--bridges/ScoopItBridge.php2
-rw-r--r--bridges/Shimmie2Bridge.php2
-rw-r--r--bridges/SoundcloudBridge.php87
-rw-r--r--bridges/StoriesIGBridge.php10
-rw-r--r--bridges/SuperbWallpapersBridge.php70
-rw-r--r--bridges/TbibBridge.php2
-rw-r--r--bridges/TheCodingLoveBridge.php2
-rw-r--r--bridges/ThePirateBayBridge.php110
-rw-r--r--bridges/TheWhiteboardBridge.php22
-rw-r--r--bridges/VarietyBridge.php30
-rw-r--r--bridges/ViceBridge.php38
-rw-r--r--bridges/VieDeMerdeBridge.php56
-rw-r--r--bridges/VkBridge.php61
-rw-r--r--bridges/XbooruBridge.php2
-rw-r--r--bridges/XenForoBridge.php12
-rw-r--r--bridges/YahtzeeDevDiaryBridge.php21
-rw-r--r--bridges/ZoneTelechargementBridge.php10
-rw-r--r--composer.json43
-rw-r--r--composer.lock1475
-rw-r--r--config.default.ini.php12
-rw-r--r--formats/AtomFormat.php4
-rw-r--r--formats/HtmlFormat.php16
-rw-r--r--formats/JsonFormat.php4
-rw-r--r--formats/MrssFormat.php4
-rw-r--r--formats/PlaintextFormat.php4
-rw-r--r--lib/BridgeAbstract.php4
-rw-r--r--lib/BridgeCard.php8
-rw-r--r--lib/Configuration.php9
-rw-r--r--lib/FormatAbstract.php8
-rw-r--r--lib/FormatInterface.php7
-rw-r--r--lib/ParameterValidator.php7
-rw-r--r--lib/contents.php25
-rw-r--r--lib/error.php34
-rw-r--r--static/connectivity.css8
-rw-r--r--static/connectivity.js256
-rw-r--r--static/style.css27
99 files changed, 10251 insertions, 656 deletions
diff --git a/README.md b/README.md
index 66632f9..a9db8ea 100644
--- a/README.md
+++ b/README.md
@@ -2,7 +2,7 @@
===
[![LICENSE](https://img.shields.io/badge/license-UNLICENSE-blue.svg)](UNLICENSE) [![GitHub release](https://img.shields.io/github/release/rss-bridge/rss-bridge.svg?logo=github)](https://github.com/rss-bridge/rss-bridge/releases/latest) [![Debian Release](https://img.shields.io/badge/dynamic/json.svg?logo=debian&label=debian%20release&url=https%3A%2F%2Fsources.debian.org%2Fapi%2Fsrc%2Frss-bridge%2F&query=%24.versions%5B0%5D.version&colorB=blue)](https://tracker.debian.org/pkg/rss-bridge) [![Guix Release](https://img.shields.io/badge/guix%20release-unknown-blue.svg)](https://www.gnu.org/software/guix/packages/R/) [![Build Status](https://travis-ci.org/RSS-Bridge/rss-bridge.svg?branch=master)](https://travis-ci.org/RSS-Bridge/rss-bridge) [![Docker Build Status](https://img.shields.io/docker/build/rssbridge/rss-bridge.svg?logo=docker)](https://hub.docker.com/r/rssbridge/rss-bridge/)
-RSS-Bridge is a PHP project capable of generating RSS and Atom feeds for websites which don't have one. It can be used on webservers or as stand alone application in CLI mode.
+RSS-Bridge is a PHP project capable of generating RSS and Atom feeds for websites that don't have one. It can be used on webservers or as a stand-alone application in CLI mode.
**Important**: RSS-Bridge is __not__ a feed reader or feed aggregator, but a tool to generate feeds that are consumed by feed readers and feed aggregators. Find a list of feed aggregators on [Wikipedia](https://en.wikipedia.org/wiki/Comparison_of_feed_aggregators).
@@ -76,7 +76,7 @@ RSS-Bridge allows you to take full control over which bridges are displayed to t
Find more information on the [Wiki](https://github.com/RSS-Bridge/rss-bridge/wiki/Whitelisting)
-**Notice**: By default RSS-Bridge will only show a small subset of bridges. Make sure to read up on [whitelisting](https://github.com/RSS-Bridge/rss-bridge/wiki/Whitelisting) to unlock the full potential of RSS-Bridge!
+**Notice**: By default, RSS-Bridge will only show a small subset of bridges. Make sure to read up on [whitelisting](https://github.com/RSS-Bridge/rss-bridge/wiki/Whitelisting) to unlock the full potential of RSS-Bridge!
Deploy
===
@@ -118,6 +118,7 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [alex73](https://github.com/alex73)
* [alexAubin](https://github.com/alexAubin)
* [AmauryCarrade](https://github.com/AmauryCarrade)
+* [AntoineTurmel](https://github.com/AntoineTurmel)
* [ArthurHoaro](https://github.com/ArthurHoaro)
* [Astalaseven](https://github.com/Astalaseven)
* [Astyan-42](https://github.com/Astyan-42)
@@ -131,6 +132,7 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [cnlpete](https://github.com/cnlpete)
* [corenting](https://github.com/corenting)
* [couraudt](https://github.com/couraudt)
+* [cyberjacob](https://github.com/cyberjacob)
* [da2x](https://github.com/da2x)
* [Daiyousei](https://github.com/Daiyousei)
* [dawidsowa](https://github.com/dawidsowa)
@@ -138,6 +140,7 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [DJCrashdummy](https://github.com/DJCrashdummy)
* [Djuuu](https://github.com/Djuuu)
* [DnAp](https://github.com/DnAp)
+* [dominik-th](https://github.com/dominik-th)
* [Draeli](https://github.com/Draeli)
* [Dreckiger-Dan](https://github.com/Dreckiger-Dan)
* [em92](https://github.com/em92)
@@ -149,6 +152,7 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [fulmeek](https://github.com/fulmeek)
* [Ginko-Aloe](https://github.com/Ginko-Aloe)
* [Glandos](https://github.com/Glandos)
+* [gloony](https://github.com/gloony)
* [GregThib](https://github.com/GregThib)
* [griffaurel](https://github.com/griffaurel)
* [Grummfy](https://github.com/Grummfy)
@@ -169,11 +173,12 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [laBecasse](https://github.com/laBecasse)
* [lagaisse](https://github.com/lagaisse)
* [lalannev](https://github.com/lalannev)
-* [Leomaradan](https://github.com/Leomaradan)
* [ldidry](https://github.com/ldidry)
+* [Leomaradan](https://github.com/Leomaradan)
* [Limero](https://github.com/Limero)
* [LogMANOriginal](https://github.com/LogMANOriginal)
* [lorenzos](https://github.com/lorenzos)
+* [lukasklinger](https://github.com/lukasklinger)
* [m0zes](https://github.com/m0zes)
* [matthewseal](https://github.com/matthewseal)
* [mcbyte-it](https://github.com/mcbyte-it)
@@ -189,6 +194,8 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [niawag](https://github.com/niawag)
* [Nono-m0le](https://github.com/Nono-m0le)
* [ObsidianWitch](https://github.com/ObsidianWitch)
+* [OliverParoczai](https://github.com/OliverParoczai)
+* [oratosquilla-oratoria](https://github.com/oratosquilla-oratoria)
* [ORelio](https://github.com/ORelio)
* [PaulVayssiere](https://github.com/PaulVayssiere)
* [pellaeon](https://github.com/pellaeon)
@@ -204,16 +211,20 @@ https://gist.github.com/LogMANOriginal/da00cd1e5f0ca31cef8e193509b17fd8
* [rogerdc](https://github.com/rogerdc)
* [Roliga](https://github.com/Roliga)
* [sebsauvage](https://github.com/sebsauvage)
+* [shutosg](https://github.com/shutosg)
* [somini](https://github.com/somini)
* [squeek502](https://github.com/squeek502)
+* [stjohnjohnson](https://github.com/stjohnjohnson)
* [Strubbl](https://github.com/Strubbl)
* [sublimz](https://github.com/sublimz)
+* [sunchaserinfo](https://github.com/sunchaserinfo)
* [sysadminstory](https://github.com/sysadminstory)
* [tameroski](https://github.com/tameroski)
* [teromene](https://github.com/teromene)
* [thefranke](https://github.com/thefranke)
* [ThePadawan](https://github.com/ThePadawan)
* [TheRadialActive](https://github.com/TheRadialActive)
+* [TitiTestScalingo](https://github.com/TitiTestScalingo)
* [triatic](https://github.com/triatic)
* [VerifiedJoseph](https://github.com/VerifiedJoseph)
* [WalterBarrett](https://github.com/WalterBarrett)
diff --git a/actions/ConnectivityAction.php b/actions/ConnectivityAction.php
new file mode 100644
index 0000000..69272dd
--- /dev/null
+++ b/actions/ConnectivityAction.php
@@ -0,0 +1,136 @@
+<?php
+/**
+ * This file is part of RSS-Bridge, a PHP project capable of generating RSS and
+ * Atom feeds for websites that don't have one.
+ *
+ * For the full license information, please view the UNLICENSE file distributed
+ * with this source code.
+ *
+ * @package Core
+ * @license http://unlicense.org/ UNLICENSE
+ * @link https://github.com/rss-bridge/rss-bridge
+ */
+
+/**
+ * Checks if the website for a given bridge is reachable.
+ *
+ * **Remarks**
+ * - This action is only available in debug mode.
+ * - Returns the bridge status as Json-formatted string.
+ * - Returns an error if the bridge is not whitelisted.
+ * - Returns a responsive web page that automatically checks all whitelisted
+ * bridges (using JavaScript) if no bridge is specified.
+ */
+class ConnectivityAction extends ActionAbstract {
+ public function execute() {
+
+ if(!Debug::isEnabled()) {
+ returnError('This action is only available in debug mode!');
+ }
+
+ if(!isset($this->userData['bridge'])) {
+ $this->returnEntryPage();
+ return;
+ }
+
+ $bridgeName = $this->userData['bridge'];
+
+ $this->reportBridgeConnectivity($bridgeName);
+
+ }
+
+ /**
+ * Generates a report about the bridge connectivity status and sends it back
+ * to the user.
+ *
+ * The report is generated as Json-formatted string in the format
+ * {
+ * "bridge": "<bridge-name>",
+ * "successful": true/false
+ * }
+ *
+ * @param string $bridgeName Name of the bridge to generate the report for
+ * @return void
+ */
+ private function reportBridgeConnectivity($bridgeName) {
+
+ $bridgeFac = new \BridgeFactory();
+ $bridgeFac->setWorkingDir(PATH_LIB_BRIDGES);
+
+ if(!$bridgeFac->isWhitelisted($bridgeName)) {
+ header('Content-Type: text/html');
+ returnServerError('Bridge is not whitelisted!');
+ }
+
+ header('Content-Type: text/json');
+
+ $retVal = array(
+ 'bridge' => $bridgeName,
+ 'successful' => false,
+ 'http_code' => 200,
+ );
+
+ $bridge = $bridgeFac->create($bridgeName);
+
+ if($bridge === false) {
+ echo json_encode($retVal);
+ return;
+ }
+
+ $curl_opts = array(
+ CURLOPT_CONNECTTIMEOUT => 5
+ );
+
+ try {
+ $reply = getContents($bridge::URI, array(), $curl_opts, true);
+
+ if($reply) {
+ $retVal['successful'] = true;
+ if (isset($reply['header'])) {
+ if (strpos($reply['header'], 'HTTP/1.1 301 Moved Permanently') !== false) {
+ $retVal['http_code'] = 301;
+ }
+ }
+ }
+ } catch(Exception $e) {
+ $retVal['successful'] = false;
+ }
+
+ echo json_encode($retVal);
+
+ }
+
+ private function returnEntryPage() {
+ echo <<<EOD
+<!DOCTYPE html>
+
+<html>
+ <head>
+ <link rel="stylesheet" href="static/bootstrap.min.css">
+ <link
+ rel="stylesheet"
+ href="https://use.fontawesome.com/releases/v5.6.3/css/all.css"
+ integrity="sha384-UHRtZLI+pbxtHCWp1t77Bi1L4ZtiqrqD80Kn4Z8NTSRyMA2Fd33n5dQ8lWUE00s/"
+ crossorigin="anonymous">
+ <link rel="stylesheet" href="static/connectivity.css">
+ <script src="static/connectivity.js" type="text/javascript"></script>
+ </head>
+ <body>
+ <div id="main-content" class="container">
+ <div class="progress">
+ <div class="progress-bar" role="progressbar" aria-valuenow="75" aria-valuemin="0" aria-valuemax="100"></div>
+ </div>
+ <div id="status-message" class="sticky-top alert alert-primary alert-dismissible fade show" role="alert">
+ <i id="status-icon" class="fas fa-sync"></i>
+ <span>...</span>
+ <button type="button" class="close" data-dismiss="alert" aria-label="Close" onclick="stopConnectivityChecks()">
+ <span aria-hidden="true">&times;</span>
+ </button>
+ </div>
+ <input type="text" class="form-control" id="search" onkeyup="search()" placeholder="Search for bridge..">
+ </div>
+ </body>
+</html>
+EOD;
+ }
+}
diff --git a/actions/DisplayAction.php b/actions/DisplayAction.php
index 9b4d363..89930cf 100644
--- a/actions/DisplayAction.php
+++ b/actions/DisplayAction.php
@@ -12,6 +12,15 @@
*/
class DisplayAction extends ActionAbstract {
+ private function get_return_code($error) {
+ $returnCode = $error->getCode();
+ if ($returnCode === 301 || $returnCode === 302) {
+ # Don't pass redirect codes to the exterior
+ $returnCode = 508;
+ }
+ return $returnCode;
+ }
+
public function execute() {
$bridge = array_key_exists('bridge', $this->userData) ? $this->userData['bridge'] : null;
@@ -146,63 +155,77 @@ class DisplayAction extends ActionAbstract {
} catch(Error $e) {
error_log($e);
- $item = new \FeedItem();
-
- // Create "new" error message every 24 hours
- $this->userData['_error_time'] = urlencode((int)(time() / 86400));
-
- // Error 0 is a special case (i.e. "trying to get property of non-object")
- if($e->getCode() === 0) {
- $item->setTitle(
- 'Bridge encountered an unexpected situation! ('
- . $this->userData['_error_time']
- . ')'
- );
- } else {
- $item->setTitle(
- 'Bridge returned error '
- . $e->getCode()
- . '! ('
- . $this->userData['_error_time']
- . ')'
- );
+ if(logBridgeError($bridge::NAME, $e->getCode()) >= Configuration::getConfig('error', 'report_limit')) {
+ if(Configuration::getConfig('error', 'output') === 'feed') {
+ $item = new \FeedItem();
+
+ // Create "new" error message every 24 hours
+ $this->userData['_error_time'] = urlencode((int)(time() / 86400));
+
+ // Error 0 is a special case (i.e. "trying to get property of non-object")
+ if($e->getCode() === 0) {
+ $item->setTitle(
+ 'Bridge encountered an unexpected situation! ('
+ . $this->userData['_error_time']
+ . ')'
+ );
+ } else {
+ $item->setTitle(
+ 'Bridge returned error '
+ . $e->getCode()
+ . '! ('
+ . $this->userData['_error_time']
+ . ')'
+ );
+ }
+
+ $item->setURI(
+ (isset($_SERVER['REQUEST_URI']) ? parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH) : '')
+ . '?'
+ . http_build_query($this->userData)
+ );
+
+ $item->setTimestamp(time());
+ $item->setContent(buildBridgeException($e, $bridge));
+
+ $items[] = $item;
+ } elseif(Configuration::getConfig('error', 'output') === 'http') {
+ header('Content-Type: text/html', true, get_return_code($e));
+ die(buildTransformException($e, $bridge));
+ }
}
-
- $item->setURI(
- (isset($_SERVER['REQUEST_URI']) ? parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH) : '')
- . '?'
- . http_build_query($this->userData)
- );
-
- $item->setTimestamp(time());
- $item->setContent(buildBridgeException($e, $bridge));
-
- $items[] = $item;
} catch(Exception $e) {
error_log($e);
- $item = new \FeedItem();
-
- // Create "new" error message every 24 hours
- $this->userData['_error_time'] = urlencode((int)(time() / 86400));
-
- $item->setURI(
- (isset($_SERVER['REQUEST_URI']) ? parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH) : '')
- . '?'
- . http_build_query($this->userData)
- );
-
- $item->setTitle(
- 'Bridge returned error '
- . $e->getCode()
- . '! ('
- . $this->userData['_error_time']
- . ')'
- );
- $item->setTimestamp(time());
- $item->setContent(buildBridgeException($e, $bridge));
-
- $items[] = $item;
+ if(logBridgeError($bridge::NAME, $e->getCode()) >= Configuration::getConfig('error', 'report_limit')) {
+ if(Configuration::getConfig('error', 'output') === 'feed') {
+ $item = new \FeedItem();
+
+ // Create "new" error message every 24 hours
+ $this->userData['_error_time'] = urlencode((int)(time() / 86400));
+
+ $item->setURI(
+ (isset($_SERVER['REQUEST_URI']) ? parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH) : '')
+ . '?'
+ . http_build_query($this->userData)
+ );
+
+ $item->setTitle(
+ 'Bridge returned error '
+ . $e->getCode()
+ . '! ('
+ . $this->userData['_error_time']
+ . ')'
+ );
+ $item->setTimestamp(time());
+ $item->setContent(buildBridgeException($e, $bridge));
+
+ $items[] = $item;
+ } elseif(Configuration::getConfig('error', 'output') === 'http') {
+ header('Content-Type: text/html', true, get_return_code($e));
+ die(buildTransformException($e, $bridge));
+ }
+ }
}
// Store data in cache
diff --git a/bridges/AmazonPriceTrackerBridge.php b/bridges/AmazonPriceTrackerBridge.php
index 6fa11c9..950178a 100644
--- a/bridges/AmazonPriceTrackerBridge.php
+++ b/bridges/AmazonPriceTrackerBridge.php
@@ -134,11 +134,11 @@ EOT;
// data-asin="B00WTHJ5SU" data-asin-price="14.99" data-asin-shipping="0"
// data-asin-currency-code="USD" data-substitute-count="-1" ... />
if ($asinData) {
- return [
+ return array(
'price' => $asinData->getAttribute('data-asin-price'),
'currency' => $asinData->getAttribute('data-asin-currency-code'),
'shipping' => $asinData->getAttribute('data-asin-shipping')
- ];
+ );
}
return false;
@@ -150,11 +150,11 @@ EOT;
preg_match('/^\s*([A-Z]{3}|£|\$)\s?([\d.,]+)\s*$/', $priceDiv->plaintext, $matches);
if (count($matches) === 3) {
- return [
+ return array(
'price' => $matches[2],
'currency' => $matches[1],
'shipping' => '0'
- ];
+ );
}
return false;
diff --git a/bridges/AppleAppStoreBridge.php b/bridges/AppleAppStoreBridge.php
new file mode 100644
index 0000000..c1403fe
--- /dev/null
+++ b/bridges/AppleAppStoreBridge.php
@@ -0,0 +1,149 @@
+<?php
+
+class AppleAppStoreBridge extends BridgeAbstract {
+
+ const MAINTAINER = 'captn3m0';
+ const NAME = 'Apple App Store';
+ const URI = 'https://apps.apple.com/';
+ const CACHE_TIMEOUT = 3600; // 1h
+ const DESCRIPTION = 'Returns version updates for a specific application';
+
+ const PARAMETERS = array(array(
+ 'id' => array(
+ 'name' => 'Application ID',
+ 'required' => true,
+ 'exampleValue' => '310633997'
+ ),
+ 'p' => array(
+ 'name' => 'Platform',
+ 'type' => 'list',
+ 'values' => array(
+ 'iPad' => 'ipad',
+ 'iPhone' => 'iphone',
+ 'Mac' => 'mac',
+
+ // The following 2 are present in responses
+ // but not yet tested
+ 'Web' => 'web',
+ 'Apple TV' => 'appletv',
+ ),
+ 'defaultValue' => 'iphone',
+ ),
+ 'country' => array(
+ 'name' => 'Store Country',
+ 'type' => 'list',
+ 'values' => array(
+ 'US' => 'US',
+ 'India' => 'IN',
+ 'Canada' => 'CA'
+ ),
+ 'defaultValue' => 'US',
+ ),
+ ));
+
+ const PLATFORM_MAPPING = array(
+ 'iphone' => 'ios',
+ 'ipad' => 'ios',
+ );
+
+ private function makeHtmlUrl($id, $country){
+ return 'https://apps.apple.com/' . $country . '/app/id' . $id;
+ }
+
+ private function makeJsonUrl($id, $platform, $country){
+ return "https://amp-api.apps.apple.com/v1/catalog/$country/apps/$id?platform=$platform&extend=versionHistory";
+ }
+
+ public function getName(){
+ if (isset($this->name)) {
+ return $this->name . ' - AppStore Updates';
+ }
+
+ return parent::getName();
+ }
+
+ /**
+ * In case of some platforms, the data is present in the initial response
+ */
+ private function getDataFromShoebox($id, $platform, $country){
+ $uri = $this->makeHtmlUrl($id, $country);
+ $html = getSimpleHTMLDOMCached($uri, 3600);
+ $script = $html->find('script[id="shoebox-ember-data-store"]', 0);
+
+ $json = json_decode($script->innertext, true);
+ return $json['data'];
+ }
+
+ private function getJWTToken($id, $platform, $country){
+ $uri = $this->makeHtmlUrl($id, $country);
+
+ $html = getSimpleHTMLDOMCached($uri, 3600);
+
+ $meta = $html->find('meta[name="web-experience-app/config/environment"]', 0);
+
+ $json = urldecode($meta->content);
+
+ $json = json_decode($json);
+
+ return $json->MEDIA_API->token;
+ }
+
+ private function getAppData($id, $platform, $country, $token){
+ $uri = $this->makeJsonUrl($id, $platform, $country);
+
+ $headers = array(
+ "Authorization: Bearer $token",
+ );
+
+ $json = json_decode(getContents($uri, $headers), true);
+
+ return $json['data'][0];
+ }
+
+ /**
+ * Parses the version history from the data received
+ * @return array list of versions with details on each element
+ */
+ private function getVersionHistory($data, $platform){
+ switch($platform) {
+ case 'mac':
+ return $data['relationships']['platforms']['data'][0]['attributes']['versionHistory'];
+ default:
+ $os = self::PLATFORM_MAPPING[$platform];
+ return $data['attributes']['platformAttributes'][$os]['versionHistory'];
+ }
+ }
+
+ public function collectData() {
+ $id = $this->getInput('id');
+ $country = $this->getInput('country');
+ $platform = $this->getInput('p');
+
+ switch ($platform) {
+ case 'mac':
+ $data = $this->getDataFromShoebox($id, $platform, $country);
+ break;
+
+ default:
+ $token = $this->getJWTToken($id, $platform, $country);
+ $data = $this->getAppData($id, $platform, $country, $token);
+ }
+
+ $versionHistory = $this->getVersionHistory($data, $platform);
+ $name = $this->name = $data['attributes']['name'];
+ $author = $data['attributes']['artistName'];
+
+ foreach ($versionHistory as $row) {
+ $item = array();
+
+ $item['content'] = nl2br($row['releaseNotes']);
+ $item['title'] = $name . ' - ' . $row['versionDisplay'];
+ $item['timestamp'] = $row['releaseDate'];
+ $item['author'] = $author;
+
+ $item['uri'] = $this->makeHtmlUrl($id, $country);
+
+ $this->items[] = $item;
+ }
+ }
+}
diff --git a/bridges/AppleMusicBridge.php b/bridges/AppleMusicBridge.php
index 5a4f40a..3011977 100644
--- a/bridges/AppleMusicBridge.php
+++ b/bridges/AppleMusicBridge.php
@@ -5,19 +5,19 @@ class AppleMusicBridge extends BridgeAbstract {
const URI = 'https://www.apple.com';
const DESCRIPTION = 'Fetches the latest releases from an artist';
const MAINTAINER = 'Limero';
- const PARAMETERS = [[
- 'url' => [
+ const PARAMETERS = array(array(
+ 'url' => array(
'name' => 'Artist URL',
'exampleValue' => 'https://itunes.apple.com/us/artist/dunderpatrullen/329796274',
'required' => true,
- ],
- 'imgSize' => [
+ ),
+ 'imgSize' => array(
'name' => 'Image size for thumbnails (in px)',
'type' => 'number',
'defaultValue' => 512,
'required' => true,
- ]
- ]];
+ )
+ ));
const CACHE_TIMEOUT = 21600; // 6 hours
public function collectData() {
@@ -36,12 +36,12 @@ class AppleMusicBridge extends BridgeAbstract {
// Loop through each object
foreach ($json->included as $obj) {
if ($obj->type === 'lockup/album') {
- $this->items[] = [
+ $this->items[] = array(
'title' => $obj->attributes->artistName . ' - ' . $obj->attributes->name,
'uri' => $obj->attributes->url,
'timestamp' => $obj->attributes->releaseDate,
'enclosures' => $obj->relationships->artwork->data->id,
- ];
+ );
} elseif ($obj->type === 'image') {
$images[$obj->id] = $obj->attributes->url;
}
@@ -49,9 +49,9 @@ class AppleMusicBridge extends BridgeAbstract {
// Add the images to each item
foreach ($this->items as &$item) {
- $item['enclosures'] = [
+ $item['enclosures'] = array(
str_replace('{w}x{h}bb.{f}', $imgSize . 'x0w.jpg', $images[$item['enclosures']]),
- ];
+ );
}
// Sort the order to put the latest albums first
diff --git a/bridges/AtmoNouvelleAquitaineBridge.php b/bridges/AtmoNouvelleAquitaineBridge.php
index 2ded81a..d395fa7 100644
--- a/bridges/AtmoNouvelleAquitaineBridge.php
+++ b/bridges/AtmoNouvelleAquitaineBridge.php
@@ -77,7 +77,7 @@ class AtmoNouvelleAquitaineBridge extends BridgeAbstract {
private function getLegendIndexes() {
$rawIndexes = $this->dom->find('.prevision-legend .prevision-legend-label');
- $indexes = [];
+ $indexes = array();
for ($i = 0; $i < count($rawIndexes); $i++) {
if ($rawIndexes[$i]->hasAttribute('data-color')) {
$indexes[$rawIndexes[$i]->getAttribute('data-color')] = $rawIndexes[$i]->innertext;
diff --git a/bridges/BandcampBridge.php b/bridges/BandcampBridge.php
index 6c75ed5..fa07146 100644
--- a/bridges/BandcampBridge.php
+++ b/bridges/BandcampBridge.php
@@ -1,71 +1,260 @@
<?php
class BandcampBridge extends BridgeAbstract {
- const MAINTAINER = 'sebsauvage';
- const NAME = 'Bandcamp Tag';
+ const MAINTAINER = 'sebsauvage, Roliga';
+ const NAME = 'Bandcamp Bridge';
const URI = 'https://bandcamp.com/';
const CACHE_TIMEOUT = 600; // 10min
- const DESCRIPTION = 'New bandcamp release by tag';
- const PARAMETERS = array( array(
- 'tag' => array(
- 'name' => 'tag',
- 'type' => 'text',
- 'required' => true
+ const DESCRIPTION = 'New bandcamp releases by tag, band or album';
+ const PARAMETERS = array(
+ 'By tag' => array(
+ 'tag' => array(
+ 'name' => 'tag',
+ 'type' => 'text',
+ 'required' => true
+ )
+ ),
+ 'By band' => array(
+ 'band' => array(
+ 'name' => 'band',
+ 'type' => 'text',
+ 'title' => 'Band name as seen in the band page URL',
+ 'required' => true
+ ),
+ 'type' => array(
+ 'name' => 'Articles are',
+ 'type' => 'list',
+ 'values' => array(
+ 'Releases' => 'releases',
+ 'Releases, new one when track list changes' => 'changes',
+ 'Individual tracks' => 'tracks'
+ ),
+ 'defaultValue' => 'changes'
+ ),
+ 'limit' => array(
+ 'name' => 'limit',
+ 'type' => 'number',
+ 'title' => 'Number of releases to return',
+ 'defaultValue' => 5
+ )
+ ),
+ 'By album' => array(
+ 'band' => array(
+ 'name' => 'band',
+ 'type' => 'text',
+ 'title' => 'Band name as seen in the album page URL',
+ 'required' => true
+ ),
+ 'album' => array(
+ 'name' => 'album',
+ 'type' => 'text',
+ 'title' => 'Album name as seen in the album page URL',
+ 'required' => true
+ ),
+ 'type' => array(
+ 'name' => 'Articles are',
+ 'type' => 'list',
+ 'values' => array(
+ 'Releases' => 'releases',
+ 'Releases, new one when track list changes' => 'changes',
+ 'Individual tracks' => 'tracks'
+ ),
+ 'defaultValue' => 'tracks'
+ )
)
- ));
+ );
const IMGURI = 'https://f4.bcbits.com/';
const IMGSIZE_300PX = 23;
const IMGSIZE_700PX = 16;
+ private $feedName;
+
public function getIcon() {
return 'https://s4.bcbits.com/img/bc_favicon.ico';
}
public function collectData(){
- $url = self::URI . 'api/hub/1/dig_deeper';
- $data = $this->buildRequestJson();
- $header = array(
- 'Content-Type: application/json',
- 'Content-Length: ' . strlen($data)
- );
- $opts = array(
- CURLOPT_CUSTOMREQUEST => 'POST',
- CURLOPT_POSTFIELDS => $data
- );
- $content = getContents($url, $header, $opts)
- or returnServerError('Could not complete request to: ' . $url);
+ switch($this->queriedContext) {
+ case 'By tag':
+ $url = self::URI . 'api/hub/1/dig_deeper';
+ $data = $this->buildRequestJson();
+ $header = array(
+ 'Content-Type: application/json',
+ 'Content-Length: ' . strlen($data)
+ );
+ $opts = array(
+ CURLOPT_CUSTOMREQUEST => 'POST',
+ CURLOPT_POSTFIELDS => $data
+ );
+ $content = getContents($url, $header, $opts)
+ or returnServerError('Could not complete request to: ' . $url);
+
+ $json = json_decode($content);
+
+ if ($json->ok !== true) {
+ returnServerError('Invalid response');
+ }
+
+ foreach ($json->items as $entry) {
+ $url = $entry->tralbum_url;
+ $artist = $entry->artist;
+ $title = $entry->title;
+ // e.g. record label is the releaser, but not the artist
+ $releaser = $entry->band_name !== $entry->artist ? $entry->band_name : null;
+
+ $full_title = $artist . ' - ' . $title;
+ $full_artist = $artist;
+ if (isset($releaser)) {
+ $full_title .= ' (' . $releaser . ')';
+ $full_artist .= ' (' . $releaser . ')';
+ }
+ $small_img = $this->getImageUrl($entry->art_id, self::IMGSIZE_300PX);
+ $img = $this->getImageUrl($entry->art_id, self::IMGSIZE_700PX);
+
+ $item = array(
+ 'uri' => $url,
+ 'author' => $full_artist,
+ 'title' => $full_title
+ );
+ $item['content'] = "<img src='$small_img' /><br/>$full_title";
+ $item['enclosures'] = array($img);
+ $this->items[] = $item;
+ }
+ break;
+ case 'By band':
+ case 'By album':
+ $html = getSimpleHTMLDOMCached($this->getURI(), 86400);
+
+ $titleElement = $html->find('head meta[name=title]', 0)
+ or returnServerError('Unable to find title on: ' . $this->getURI());
+ $this->feedName = $titleElement->content;
+
+ $regex = '/band_id=(\d+)/';
+ if(preg_match($regex, $html, $matches) == false)
+ returnServerError('Unable to find band ID on: ' . $this->getURI());
+ $band_id = $matches[1];
+
+ $tralbums = array();
+ switch($this->queriedContext) {
+ case 'By band':
+ $query_data = array(
+ 'band_id' => $band_id
+ );
+ $band_data = $this->apiGet('mobile/22/band_details', $query_data);
- $json = json_decode($content);
+ $num_albums = min(count($band_data->discography), $this->getInput('limit'));
+ for($i = 0; $i < $num_albums; $i++) {
+ $album_basic_data = $band_data->discography[$i];
- if ($json->ok !== true) {
- returnServerError('Invalid response');
+ // 'a' or 't' for albums and individual tracks respectively
+ $tralbum_type = substr($album_basic_data->item_type, 0, 1);
+
+ $query_data = array(
+ 'band_id' => $band_id,
+ 'tralbum_type' => $tralbum_type,
+ 'tralbum_id' => $album_basic_data->item_id
+ );
+ $tralbums[] = $this->apiGet('mobile/22/tralbum_details', $query_data);
+ }
+ break;
+ case 'By album':
+ $regex = '/album=(\d+)/';
+ if(preg_match($regex, $html, $matches) == false)
+ returnServerError('Unable to find album ID on: ' . $this->getURI());
+ $album_id = $matches[1];
+
+ $query_data = array(
+ 'band_id' => $band_id,
+ 'tralbum_type' => 'a',
+ 'tralbum_id' => $album_id
+ );
+ $tralbums[] = $this->apiGet('mobile/22/tralbum_details', $query_data);
+
+ break;
+ }
+
+ foreach ($tralbums as $tralbum_data) {
+ if ($tralbum_data->type === 'a' && $this->getInput('type') === 'tracks') {
+ foreach ($tralbum_data->tracks as $track) {
+ $query_data = array(
+ 'band_id' => $band_id,
+ 'tralbum_type' => 't',
+ 'tralbum_id' => $track->track_id
+ );
+ $track_data = $this->apiGet('mobile/22/tralbum_details', $query_data);
+
+ $this->items[] = $this->buildTralbumItem($track_data);
+ }
+ } else {
+ $this->items[] = $this->buildTralbumItem($tralbum_data);
+ }
+ }
+ break;
}
+ }
+
+ private function buildTralbumItem($tralbum_data){
+ $band_data = $tralbum_data->band;
+
+ // Format title like: ARTIST - ALBUM/TRACK (OPTIONAL RELEASER)
+ // Format artist/author like: ARTIST (OPTIONAL RELEASER)
+ //
+ // If the album/track is released under a label/a band other than the artist
+ // themselves, append that releaser name to the title and artist/author.
+ //
+ // This sadly doesn't always work right for individual tracks as the artist
+ // of the track is always set to the releaser.
+ $artist = $tralbum_data->tralbum_artist;
+ $full_title = $artist . ' - ' . $tralbum_data->title;
+ $full_artist = $artist;
+ if (isset($tralbum_data->label)) {
+ $full_title .= ' (' . $tralbum_data->label . ')';
+ $full_artist .= ' (' . $tralbum_data->label . ')';
+ } elseif ($band_data->name !== $artist) {
+ $full_title .= ' (' . $band_data->name . ')';
+ $full_artist .= ' (' . $band_data->name . ')';
+ }
+
+ $small_img = $this->getImageUrl($tralbum_data->art_id, self::IMGSIZE_300PX);
+ $img = $this->getImageUrl($tralbum_data->art_id, self::IMGSIZE_700PX);
+
+ $item = array(
+ 'uri' => $tralbum_data->bandcamp_url,
+ 'author' => $full_artist,
+ 'title' => $full_title,
+ 'enclosures' => array($img),
+ 'timestamp' => $tralbum_data->release_date
+ );
- foreach ($json->items as $entry) {
- $url = $entry->tralbum_url;
- $artist = $entry->artist;
- $title = $entry->title;
- // e.g. record label is the releaser, but not the artist
- $releaser = $entry->band_name !== $entry->artist ? $entry->band_name : null;
-
- $full_title = $artist . ' - ' . $title;
- $full_artist = $artist;
- if (isset($releaser)) {
- $full_title .= ' (' . $releaser . ')';
- $full_artist .= ' (' . $releaser . ')';
+ $item['categories'] = array();
+ foreach ($tralbum_data->tags as $tag) {
+ $item['categories'][] = $tag->norm_name;
+ }
+
+ // Give articles a unique UID depending on its track list
+ // Releases should then show up as new articles when tracks are added
+ if ($this->getInput('type') === 'changes') {
+ $item['uid'] = "bandcamp/$band_data->band_id/$tralbum_data->id/";
+ foreach ($tralbum_data->tracks as $track) {
+ $item['uid'] .= $track->track_id;
}
- $small_img = $this->getImageUrl($entry->art_id, self::IMGSIZE_300PX);
- $img = $this->getImageUrl($entry->art_id, self::IMGSIZE_700PX);
+ }
- $item = array(
- 'uri' => $url,
- 'author' => $full_artist,
- 'title' => $full_title
- );
- $item['content'] = "<img src='$small_img' /><br/>$full_title";
- $item['enclosures'] = array($img);
- $this->items[] = $item;
+ $item['content'] = "<img src='$small_img' /><br/>$full_title<br/>";
+ if ($tralbum_data->type === 'a') {
+ $item['content'] .= '<ol>';
+ foreach ($tralbum_data->tracks as $track) {
+ $item['content'] .= "<li>$track->title</li>";
+ }
+ $item['content'] .= '</ol>';
+ }
+ if (!empty($tralbum_data->about)) {
+ $item['content'] .= '<p>'
+ . nl2br($tralbum_data->about)
+ . '</p>';
}
+
+ return $item;
}
private function buildRequestJson(){
@@ -81,11 +270,94 @@ class BandcampBridge extends BridgeAbstract {
return self::IMGURI . 'img/a' . $id . '_' . $size . '.jpg';
}
+ private function apiGet($endpoint, $query_data) {
+ $url = self::URI . 'api/' . $endpoint . '?' . http_build_query($query_data);
+ $data = json_decode(getContents($url))
+ or returnServerError('API request to "' . $url . '" failed.');
+ return $data;
+ }
+
+ public function getURI(){
+ switch($this->queriedContext) {
+ case 'By tag':
+ if(!is_null($this->getInput('tag'))) {
+ return self::URI
+ . 'tag/'
+ . urlencode($this->getInput('tag'))
+ . '?sort_field=date';
+ }
+ break;
+ case 'By band':
+ if(!is_null($this->getInput('band'))) {
+ return 'https://'
+ . $this->getInput('band')
+ . '.bandcamp.com/music';
+ }
+ break;
+ case 'By album':
+ if(!is_null($this->getInput('band')) && !is_null($this->getInput('album'))) {
+ return 'https://'
+ . $this->getInput('band')
+ . '.bandcamp.com/album/'
+ . $this->getInput('album');
+ }
+ break;
+ }
+
+ return parent::getURI();
+ }
+
public function getName(){
- if(!is_null($this->getInput('tag'))) {
- return $this->getInput('tag') . ' - Bandcamp Tag';
+ switch($this->queriedContext) {
+ case 'By tag':
+ if(!is_null($this->getInput('tag'))) {
+ return $this->getInput('tag') . ' - Bandcamp Tag';
+ }
+ break;
+ case 'By band':
+ if(isset($this->feedName)) {
+ return $this->feedName . ' - Bandcamp Band';
+ } elseif(!is_null($this->getInput('band'))) {
+ return $this->getInput('band') . ' - Bandcamp Band';
+ }
+ break;
+ case 'By album':
+ if(isset($this->feedName)) {
+ return $this->feedName . ' - Bandcamp Album';
+ } elseif(!is_null($this->getInput('album'))) {
+ return $this->getInput('album') . ' - Bandcamp Album';
+ }
+ break;
}
return parent::getName();
}
+
+ public function detectParameters($url) {
+ $params = array();
+
+ // By tag
+ $regex = '/^(https?:\/\/)?bandcamp\.com\/tag\/([^\/.&?\n]+)/';
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['tag'] = urldecode($matches[2]);
+ return $params;
+ }
+
+ // By band
+ $regex = '/^(https?:\/\/)?([^\/.&?\n]+?)\.bandcamp\.com/';
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['band'] = urldecode($matches[2]);
+ return $params;
+ }
+
+ // By album
+ $regex = '/^(https?:\/\/)?([^\/.&?\n]+?)\.bandcamp\.com\/album\/([^\/.&?\n]+)/';
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['band'] = urldecode($matches[2]);
+ $params['album'] = urldecode($matches[3]);
+ return $params;
+ }
+
+ return null;
+ }
}
diff --git a/bridges/BastaBridge.php b/bridges/BastaBridge.php
index 17d3da7..613005f 100644
--- a/bridges/BastaBridge.php
+++ b/bridges/BastaBridge.php
@@ -3,17 +3,11 @@ class BastaBridge extends BridgeAbstract {
const MAINTAINER = 'qwertygc';
const NAME = 'Bastamag Bridge';
- const URI = 'http://www.bastamag.net/';
+ const URI = 'https://www.bastamag.net/';
const CACHE_TIMEOUT = 7200; // 2h
const DESCRIPTION = 'Returns the newest articles.';
public function collectData(){
- // Replaces all relative image URLs by absolute URLs.
- // Relative URLs always start with 'local/'!
- function replaceImageUrl($content){
- return preg_replace('/src=["\']{1}([^"\']+)/ims', 'src=\'' . self::URI . '$1\'', $content);
- }
-
$html = getSimpleHTMLDOM(self::URI . 'spip.php?page=backend')
or returnServerError('Could not request Bastamag.');
@@ -25,7 +19,13 @@ class BastaBridge extends BridgeAbstract {
$item['title'] = $element->find('title', 0)->innertext;
$item['uri'] = $element->find('guid', 0)->plaintext;
$item['timestamp'] = strtotime($element->find('dc:date', 0)->plaintext);
- $item['content'] = replaceImageUrl(getSimpleHTMLDOM($item['uri'])->find('div.texte', 0)->innertext);
+ // Replaces all relative image URLs by absolute URLs.
+ // Relative URLs always start with 'local/'!
+ $item['content'] = preg_replace(
+ '/src=["\']{1}([^"\']+)/ims',
+ 'src=\'' . self::URI . '$1\'',
+ getSimpleHTMLDOM($item['uri'])->find('div.texte', 0)->innertext
+ );
$this->items[] = $item;
$limit++;
}
diff --git a/bridges/BingSearchBridge.php b/bridges/BingSearchBridge.php
index eb8a5fc..357feb6 100644
--- a/bridges/BingSearchBridge.php
+++ b/bridges/BingSearchBridge.php
@@ -92,7 +92,7 @@ class BingSearchBridge extends BridgeAbstract
or returnServerError('Could not request ' . self::NAME);
$sizeKey = $this->getInput('image_size');
- $items = [];
+ $items = array();
foreach ($html->find('a.iusc') as $element) {
$data = json_decode(htmlspecialchars_decode($element->getAttribute('m')), true);
diff --git a/bridges/BloombergBridge.php b/bridges/BloombergBridge.php
deleted file mode 100644
index 9eb1219..0000000
--- a/bridges/BloombergBridge.php
+++ /dev/null
@@ -1,69 +0,0 @@
-<?php
-class BloombergBridge extends BridgeAbstract
-{
- const NAME = 'Bloomberg';
- const URI = 'https://www.bloomberg.com/';
- const DESCRIPTION = 'Trending stories from Bloomberg';
- const MAINTAINER = 'mdemoss';
-
- const PARAMETERS = array(
- 'Trending Stories' => array(),
- 'From Search' => array(
- 'q' => array(
- 'name' => 'Keyword',
- 'required' => true
- )
- )
- );
-
- public function getName()
- {
- switch($this->queriedContext) {
- case 'Trending Stories':
- return self::NAME . ' Trending Stories';
- case 'From Search':
- if (!is_null($this->getInput('q'))) {
- return self::NAME . ' Search : ' . $this->getInput('q');
- }
- break;
- }
-
- return parent::getName();
- }
-
- public function getIcon() {
- return 'https://assets.bwbx.io/s3/javelin/public/hub/images/favicon-black-63fe5249d3.png';
- }
-
- public function collectData()
- {
- switch($this->queriedContext) {
- case 'Trending Stories': // Get list of top new <article>s from the front page.
- $html = getSimpleHTMLDOMCached($this->getURI(), 300);
- $stories = $html->find('ul.top-news-v3__stories article.top-news-v3-story');
- break;
- case 'From Search': // Get list of <article> elements from search.
- $html = getSimpleHTMLDOMCached(
- $this->getURI() .
- 'search?sort=time:desc&page=1&query=' .
- urlencode($this->getInput('q')), 300
- );
- $stories = $html->find('div.search-result-items article.search-result-story');
- break;
- }
- foreach ($stories as $element) {
- $item['uri'] = $element->find('h1 a', 0)->href;
- if (preg_match('#^https://#i', $item['uri']) !== 1) {
- $item['uri'] = $this->getURI() . $item['uri'];
- }
- $articleHtml = getSimpleHTMLDOMCached($item['uri']);
- if (!$articleHtml) {
- continue;
- }
- $item['title'] = $element->find('h1 a', 0)->plaintext;
- $item['timestamp'] = strtotime($articleHtml->find('meta[name=iso-8601-publish-date],meta[name=date]', 0)->content);
- $item['content'] = $articleHtml->find('meta[name=description]', 0)->content;
- $this->items[] = $item;
- }
- }
-}
diff --git a/bridges/CNETFranceBridge.php b/bridges/CNETFranceBridge.php
index 222c8b9..d005fd1 100644
--- a/bridges/CNETFranceBridge.php
+++ b/bridges/CNETFranceBridge.php
@@ -23,8 +23,8 @@ class CNETFranceBridge extends FeedExpander
)
);
- private $bannedTitle = [];
- private $bannedURL = [];
+ private $bannedTitle = array();
+ private $bannedURL = array();
public function collectData()
{
diff --git a/bridges/CachetBridge.php b/bridges/CachetBridge.php
index a60b8f7..75b1801 100644
--- a/bridges/CachetBridge.php
+++ b/bridges/CachetBridge.php
@@ -22,7 +22,7 @@ class CachetBridge extends BridgeAbstract {
);
const CACHE_TIMEOUT = 300;
- private $componentCache = [];
+ private $componentCache = array();
public function getURI() {
return $this->getInput('host') === null ? 'https://cachethq.io/' : $this->getInput('host');
@@ -114,13 +114,13 @@ class CachetBridge extends BridgeAbstract {
$uidOrig = $permalink . $incident->created_at;
$uid = hash('sha512', $uidOrig);
$timestamp = strtotime($incident->created_at);
- $categories = [];
+ $categories = array();
$categories[] = $incident->human_status;
if ($componentName !== '') {
$categories[] = $componentName;
}
- $item = [];
+ $item = array();
$item['uri'] = $permalink;
$item['title'] = $title;
$item['timestamp'] = $timestamp;
diff --git a/bridges/CastorusBridge.php b/bridges/CastorusBridge.php
index c394283..fbd5007 100644
--- a/bridges/CastorusBridge.php
+++ b/bridges/CastorusBridge.php
@@ -2,7 +2,7 @@
class CastorusBridge extends BridgeAbstract {
const MAINTAINER = 'logmanoriginal';
const NAME = 'Castorus Bridge';
- const URI = 'http://www.castorus.com';
+ const URI = 'https://www.castorus.com';
const CACHE_TIMEOUT = 600; // 10min
const DESCRIPTION = 'Returns the latest changes';
diff --git a/bridges/CollegeDeFranceBridge.php b/bridges/CollegeDeFranceBridge.php
index 1f81683..9640c86 100644
--- a/bridges/CollegeDeFranceBridge.php
+++ b/bridges/CollegeDeFranceBridge.php
@@ -3,7 +3,7 @@ class CollegeDeFranceBridge extends BridgeAbstract {
const MAINTAINER = 'pit-fgfjiudghdf';
const NAME = 'CollegeDeFrance';
- const URI = 'http://www.college-de-france.fr/';
+ const URI = 'https://www.college-de-france.fr/';
const CACHE_TIMEOUT = 10800; // 3h
const DESCRIPTION = 'Returns the latest audio and video from CollegeDeFrance';
diff --git a/bridges/ComicsKingdomBridge.php b/bridges/ComicsKingdomBridge.php
new file mode 100644
index 0000000..b6228dc
--- /dev/null
+++ b/bridges/ComicsKingdomBridge.php
@@ -0,0 +1,65 @@
+<?php
+class ComicsKingdomBridge extends BridgeAbstract {
+
+ const MAINTAINER = 'stjohnjohnson';
+ const NAME = 'Comics Kingdom Unofficial RSS';
+ const URI = 'https://www.comicskingdom.com/';
+ const CACHE_TIMEOUT = 21600; // 6h
+ const DESCRIPTION = 'Comics Kingdom Unofficial RSS';
+ const PARAMETERS = array( array(
+ 'comicname' => array(
+ 'name' => 'comicname',
+ 'type' => 'text',
+ 'required' => true
+ )
+ ));
+
+ public function collectData(){
+ $html = getSimpleHTMLDOM($this->getURI(), array(), array(), true, false)
+ or returnServerError('Could not request Comics Kingdom: ' . $this->getURI());
+
+ // Get author from first page
+ $author = $html->find('div.author p', 0)->plaintext
+ or returnServerError('Comics Kingdom comic does not exist: ' . $this->getURI());;
+
+ // Get current date/link
+ $link = $html->find('meta[property=og:url]', 0)->content;
+ for($i = 0; $i < 5; $i++) {
+ $item = array();
+
+ $page = getSimpleHTMLDOM($link)
+ or returnServerError('Could not request Comics Kingdom: ' . $link);
+
+ $imagelink = $page->find('meta[property=og:image]', 0)->content;
+ $prevSlug = $page->find('slider-arrow[:is-left-arrow=true]', 0);
+ $link = $this->getURI() . '/' . $prevSlug->getAttribute('date-slug');
+
+ $date = explode('/', $link);
+
+ $item['id'] = $imagelink;
+ $item['uri'] = $link;
+ $item['author'] = $author;
+ $item['title'] = 'Comics Kingdom ' . $this->getInput('comicname');
+ $item['timestamp'] = DateTime::createFromFormat('Y-m-d', $date[count($date) - 1])->getTimestamp();
+ $item['content'] = '<img src="' . $imagelink . '" />';
+
+ $this->items[] = $item;
+ }
+ }
+
+ public function getURI(){
+ if(!is_null($this->getInput('comicname'))) {
+ return self::URI . urlencode($this->getInput('comicname'));
+ }
+
+ return parent::getURI();
+ }
+
+ public function getName(){
+ if(!is_null($this->getInput('comicname'))) {
+ return $this->getInput('comicname') . ' - Comics Kingdom';
+ }
+
+ return parent::getName();
+ }
+}
diff --git a/bridges/ContainerLinuxReleasesBridge.php b/bridges/ContainerLinuxReleasesBridge.php
index d2f6325..d459b0f 100644
--- a/bridges/ContainerLinuxReleasesBridge.php
+++ b/bridges/ContainerLinuxReleasesBridge.php
@@ -10,20 +10,20 @@ class ContainerLinuxReleasesBridge extends BridgeAbstract {
const BETA = 'beta';
const ALPHA = 'alpha';
- const PARAMETERS = [
- [
- 'channel' => [
+ const PARAMETERS = array(
+ array(
+ 'channel' => array(
'name' => 'Release Channel',
'type' => 'list',
'defaultValue' => self::STABLE,
- 'values' => [
+ 'values' => array(
'Stable' => self::STABLE,
'Beta' => self::BETA,
'Alpha' => self::ALPHA,
- ],
- ]
- ]
- ];
+ ),
+ )
+ )
+ );
private function getReleaseFeed($jsonUrl) {
$json = getContents($jsonUrl)
@@ -39,7 +39,7 @@ class ContainerLinuxReleasesBridge extends BridgeAbstract {
$data = $this->getReleaseFeed($this->getJsonUri());
foreach ($data as $releaseVersion => $release) {
- $item = [];
+ $item = array();
$item['uri'] = "https://coreos.com/releases/#$releaseVersion";
$item['title'] = $releaseVersion;
diff --git a/bridges/DarkReadingBridge.php b/bridges/DarkReadingBridge.php
new file mode 100644
index 0000000..3baaad7
--- /dev/null
+++ b/bridges/DarkReadingBridge.php
@@ -0,0 +1,79 @@
+<?php
+class DarkReadingBridge extends FeedExpander {
+ const MAINTAINER = 'ORelio';
+ const NAME = 'Dark Reading Bridge';
+ const URI = 'https://www.darkreading.com/';
+ const DESCRIPTION = 'Returns the newest articles from Dark Reading';
+
+ const PARAMETERS = array( array(
+ 'feed' => array(
+ 'name' => 'Feed',
+ 'type' => 'list',
+ 'values' => array(
+ 'All Dark Reading Stories' => '000_AllArticles',
+ 'Attacks/Breaches' => '644_Attacks/Breaches',
+ 'Application Security' => '645_Application%20Security',
+ 'Database Security' => '646_Database%20Security',
+ 'Cloud' => '647_Cloud',
+ 'Endpoint' => '648_Endpoint',
+ 'Authentication' => '649_Authentication',
+ 'Privacy' => '650_Privacy',
+ 'Mobile' => '651_Mobile',
+ 'Perimeter' => '652_Perimeter',
+ 'Risk' => '653_Risk',
+ 'Compliance' => '654_Compliance',
+ 'Operations' => '655_Operations',
+ 'Careers and People' => '656_Careers%20and%20People',
+ 'Identity and Access Management' => '657_Identity%20and%20Access%20Management',
+ 'Analytics' => '658_Analytics',
+ 'Threat Intelligence' => '659_Threat%20Intelligence',
+ 'Security Monitoring' => '660_Security%20Monitoring',
+ 'Vulnerabilities / Threats' => '661_Vulnerabilities%20/%20Threats',
+ 'Advanced Threats' => '662_Advanced%20Threats',
+ 'Insider Threats' => '663_Insider%20Threats',
+ 'Vulnerability Management' => '664_Vulnerability%20Management',
+ )
+ )
+ ));
+
+ public function collectData(){
+ $feed = $this->getInput('feed');
+ $feed_splitted = explode('_', $feed);
+ $feed_id = $feed_splitted[0];
+ $feed_name = $feed_splitted[1];
+ if(empty($feed) || !ctype_digit($feed_id) || !preg_match('/[A-Za-z%20\/]/', $feed_name)) {
+ returnClientError('Invalid feed, please check the "feed" parameter.');
+ }
+ $feed_url = $this->getURI() . 'rss_simple.asp';
+ if ($feed_id != '000') {
+ $feed_url .= '?f_n=' . $feed_id . '&f_ln=' . $feed_name;
+ }
+ $this->collectExpandableDatas($feed_url);
+ }
+
+ protected function parseItem($newsItem){
+ $item = parent::parseItem($newsItem);
+ $article = getSimpleHTMLDOMCached($item['uri'])
+ or returnServerError('Could not request Dark Reading: ' . $item['uri']);
+ $item['content'] = $this->extractArticleContent($article);
+ $item['enclosures'] = array(); //remove author profile picture
+ return $item;
+ }
+
+ private function extractArticleContent($article){
+ $content = $article->find('div#article-main', 0)->innertext;
+
+ foreach (array(
+ '<div class="divsplitter',
+ '<div style="float: left; margin-right: 2px;',
+ '<div class="more-insights',
+ '<div id="more-insights',
+ ) as $div_start) {
+ $content = stripRecursiveHTMLSection($content, 'div', $div_start);
+ }
+
+ $content = stripWithDelimiters($content, '<h1 ', '</h1>');
+
+ return $content;
+ }
+}
diff --git a/bridges/DesoutterBridge.php b/bridges/DesoutterBridge.php
index 0aae41a..38761ed 100644
--- a/bridges/DesoutterBridge.php
+++ b/bridges/DesoutterBridge.php
@@ -116,6 +116,12 @@ class DesoutterBridge extends BridgeAbstract {
'name' => 'Load full articles',
'type' => 'checkbox',
'title' => 'Enable to load the full article for each item'
+ ),
+ 'limit' => array(
+ 'name' => 'Limit',
+ 'type' => 'number',
+ 'defaultValue' => 3,
+ 'title' => "Maximum number of items to return in the feed.\n0 = unlimited"
)
)
);
@@ -156,6 +162,8 @@ class DesoutterBridge extends BridgeAbstract {
$this->title = html_entity_decode($html->find('title', 0)->plaintext, ENT_QUOTES);
+ $limit = $this->getInput('limit') ?: 0;
+
foreach($html->find('article') as $article) {
$item = array();
@@ -169,6 +177,8 @@ class DesoutterBridge extends BridgeAbstract {
}
$this->items[] = $item;
+
+ if ($limit > 0 && count($this->items) >= $limit) break;
}
}
diff --git a/bridges/DiarioDoAlentejoBridge.php b/bridges/DiarioDoAlentejoBridge.php
new file mode 100644
index 0000000..806f803
--- /dev/null
+++ b/bridges/DiarioDoAlentejoBridge.php
@@ -0,0 +1,60 @@
+<?php
+class DiarioDoAlentejoBridge extends BridgeAbstract {
+ const MAINTAINER = 'somini';
+ const NAME = 'Diário do Alentejo';
+ const URI = 'https://www.diariodoalentejo.pt';
+ const DESCRIPTION = 'Semanário Regionalista Independente';
+ const CACHE_TIMEOUT = 28800; // 8h
+
+ /* This is used to hack around obtaining a timestamp. It's just a list of Month names in Portuguese ... */
+ const PT_MONTH_NAMES = array(
+ 'janeiro',
+ 'fevereiro',
+ 'março',
+ 'abril',
+ 'maio',
+ 'junho',
+ 'julho',
+ 'agosto',
+ 'setembro',
+ 'outubro',
+ 'novembro',
+ 'dezembro');
+
+ public function getIcon() {
+ return 'https://www.diariodoalentejo.pt/images/favicon/apple-touch-icon.png';
+ }
+
+ public function collectData(){
+ /* This is slow as molasses (>30s!), keep the cache timeout high to avoid killing the host */
+ $html = getSimpleHTMLDOMCached($this->getURI() . '/pt/noticias-listagem.aspx')
+ or returnServerError('Could not load content');
+
+ foreach($html->find('.list_news .item') as $element) {
+ $item = array();
+
+ $item_link = $element->find('.body h2.title a', 0);
+ /* Another broken URL, see also `bridges/ComboiosDePortugalBridge.php` */
+ $item['uri'] = self::URI . implode('/', array_map('urlencode', explode('/', $item_link->href)));
+ $item['title'] = $item_link->innertext;
+
+ $item['timestamp'] = str_ireplace(
+ array_map(function($name) { return ' ' . $name . ' '; }, self::PT_MONTH_NAMES),
+ array_map(function($num) { return sprintf('-%02d-', $num); }, range(1, sizeof(self::PT_MONTH_NAMES))),
+ $element->find('span.date', 0)->innertext);
+
+ /* Fix the Image URL */
+ $item_image = $element->find('img.thumb', 0);
+ $item_image->src = preg_replace('/.*&img=([^&]+).*/', '\1', $item_image->getAttribute('data-src'));
+
+ /* Content: */
+ /* - Image */
+ /* - Category */
+ $content = $item_image .
+ '<center>' . $element->find('a.category', 0) . '</center>';
+ $item['content'] = defaultLinkTo($content, self::URI);
+
+ $this->items[] = $item;
+ }
+ }
+}
diff --git a/bridges/DownDetectorBridge.php b/bridges/DownDetectorBridge.php
new file mode 100644
index 0000000..4aef372
--- /dev/null
+++ b/bridges/DownDetectorBridge.php
@@ -0,0 +1,6195 @@
+<?php
+class DownDetectorBridge extends BridgeAbstract {
+
+ const MAINTAINER = 'teromene';
+ const NAME = 'DownDetector Bridge';
+ const URI = 'https://downdetector.com/';
+ const DESCRIPTION = 'Returns most recent downtimes from DownDetector';
+ const CACHE_TIMEOUT = 300; // 5 min
+
+ const PARAMETERS = array(
+ 'All Websites' => array(
+ 'country' => array(
+ 'type' => 'list',
+ 'name' => 'Country',
+ 'values' => array(
+ 'Argentina' => 'https://downdetector.com.ar',
+ 'Australia' => 'https://downdetector.com.au',
+ 'België' => 'https://allestoringen.be',
+ 'Brasil' => 'https://downdetector.com.br',
+ 'Canada' => 'https://downdetector.ca',
+ 'Chile' => 'https://downdetector.cl',
+ 'Colombia' => 'https://downdetector.com.co',
+ 'Danmark' => 'https://downdetector.dk',
+ 'Deutschland' => 'https://allestörungen.de',
+ 'Ecuador' => 'https://downdetector.ec',
+ 'España' => 'https://downdetector.es',
+ 'France' => 'https://downdetector.fr',
+ 'Hong Kong' => 'https://downdetector.hk',
+ 'Hrvatska' => 'https://downdetector.hr',
+ 'India' => 'https://downdetector.in',
+ 'Indonesia' => 'https://downdetector.id',
+ 'Ireland' => 'https://downdetector.ie',
+ 'Italia' => 'https://downdetector.it',
+ 'Magyarország' => 'https://downdetector.hu',
+ 'Malaysia' => 'https://downdetector.my',
+ 'México' => 'https://downdetector.mx',
+ 'Nederland' => 'https://allestoringen.nl',
+ 'New Zealand' => 'https://downdetector.co.nz',
+ 'Norge' => 'https://downdetector.no',
+ 'Pakistan' => 'https://downdetector.pk',
+ 'Perú' => 'https://downdetector.pe',
+ 'Pilipinas' => 'https://downdetector.ph',
+ 'Polska' => 'https://downdetector.pl',
+ 'Portugal' => 'https://downdetector.pt',
+ 'România' => 'https://downdetector.ro',
+ 'Schweiz' => 'https://allestörungen.ch',
+ 'Singapore' => 'https://downdetector.sg',
+ 'Slovensko' => 'https://downdetector.sk',
+ 'South Africa' => 'https://downdetector.co.za',
+ 'Suomi' => 'https://downdetector.fi',
+ 'Sverige' => 'https://downdetector.se',
+ 'Türkiye' => 'https://downdetector.web.tr',
+ 'UAE' => 'https://downdetector.ae',
+ 'UK' => 'https://downdetector.co.uk',
+ 'United States' => 'https://downdetector.com',
+ 'Österreich' => 'https://allestörungen.at',
+ 'Česko' => 'https://downdetector.cz',
+ 'Ελλάς' => 'https://downdetector.gr',
+ 'Россия' => 'https://downdetector.ru',
+ '日本' => 'https://downdetector.jp'
+ )
+ )
+ ),
+ 'Specific Website' => array(
+ 'website' => array(
+ 'type' => 'list',
+ 'name' => 'Website',
+ 'values' => array(
+ 'Österreich' => array(
+ '1&1' => 35086,
+ '3 (Drei)' => 33546,
+ 'A1' => 33543,
+ 'Alexa' => 36919,
+ 'Amazon' => 33506,
+ 'Amazon Prime Video' => 35085,
+ 'Amino Apps' => 39034,
+ 'Anthem' => 38200,
+ 'Apex Legends' => 38117,
+ 'App Store' => 35584,
+ 'Bank Austria' => 34715,
+ 'Battlefield' => 38051,
+ 'BAWAG' => 34716,
+ 'Binance' => 36938,
+ 'Blizzard Battle.net' => 35087,
+ 'Bob' => 34953,
+ 'Boom Beach' => 34781,
+ 'Bwin' => 35071,
+ 'Call of Duty' => 34156,
+ 'Car2Go' => 34554,
+ 'Clash of Clans' => 35088,
+ 'Clash Royale' => 38357,
+ 'Coinbase' => 36804,
+ 'Counter-strike' => 35055,
+ 'Crunchyroll' => 38092,
+ 'Dazn' => 36508,
+ 'Dead By Daylight' => 37414,
+ 'Deezer' => 33832,
+ 'Destiny' => 34954,
+ 'DHL' => 36747,
+ 'Discord' => 36768,
+ 'Dota 2' => 35398,
+ 'Dropbox' => 33509,
+ 'EA' => 34502,
+ 'Easybank' => 36992,
+ 'eBay' => 33510,
+ 'Emerion' => 34613,
+ 'Epic Games Store' => 39021,
+ 'Erste Bank und Sparkasse' => 36724,
+ 'Facebook' => 33511,
+ 'Facebook Messenger' => 33512,
+ 'Fifa' => 37605,
+ 'Flickr' => 33513,
+ 'For Honor' => 35996,
+ 'Fortnite' => 36689,
+ 'Ghost Recon' => 36009,
+ 'Gmail' => 33514,
+ 'GMX' => 33515,
+ 'Google' => 33516,
+ 'Google Hangouts' => 33517,
+ 'Google Play' => 33518,
+ 'GTA 5' => 35082,
+ 'Guild Wars 2' => 36473,
+ 'Handy Parken' => 34316,
+ 'Hay Day' => 34854,
+ 'Hello Bank' => 37010,
+ 'HoT' => 38751,
+ 'iCloud' => 35501,
+ 'ICQ' => 33520,
+ 'ING DiBa' => 35129,
+ 'Instagram' => 33522,
+ 'iTunes' => 33523,
+ 'Kabelplus' => 34473,
+ 'Kik' => 33524,
+ 'Kraken' => 36770,
+ 'League of Legends' => 34350,
+ 'LinkedIn' => 33525,
+ 'Liwest' => 34471,
+ 'Lovoo' => 35079,
+ 'Magenta' => 38440,
+ 'Maxdome' => 35084,
+ 'Minecraft' => 36432,
+ 'Mittwald' => 36987,
+ 'N26' => 38834,
+ 'Netatmo' => 37956,
+ 'Netflix' => 34631,
+ 'Nintendo Network' => 35523,
+ 'Nitrado' => 35548,
+ 'NordVPN' => 38587,
+ 'Office 365' => 35120,
+ 'OneDrive' => 35412,
+ 'ORF' => 35600,
+ 'Origin' => 36889,
+ 'Outlook' => 35083,
+ 'Overwatch' => 36153,
+ 'Path of Exile' => 37730,
+ 'Paypal' => 35399,
+ 'Playerunknown\'s Battlegrounds' => 36488,
+ 'Playstation Network' => 33526,
+ 'Pokémon Go' => 35745,
+ 'Quizduell' => 34528,
+ 'Raiffeisen Bank' => 38750,
+ 'Rainbow Six' => 35563,
+ 'Red Dead Redemption' => 37739,
+ 'Reddit' => 36827,
+ 'Rocket League' => 35485,
+ 'roNET' => 37041,
+ 'Salzburg AG Cablelink' => 35601,
+ 'Shpock' => 38681,
+ 'Sky' => 35081,
+ 'Sky Ticket' => 35142,
+ 'Skype' => 33527,
+ 'Smart Hub' => 35400,
+ 'Snapchat' => 33528,
+ 'Spotify' => 33529,
+ 'Spusu' => 35598,
+ 'Steam' => 34117,
+ 'Teamviewer' => 35686,
+ 'Tele2' => 34339,
+ 'Telegram' => 34903,
+ 'Telering' => 34952,
+ 'The Division' => 35599,
+ 'The elder scrolls online' => 37160,
+ 'The Simpsons Tapped Out' => 37283,
+ 'Threema' => 34255,
+ 'Tinder' => 34243,
+ 'Tipico' => 36515,
+ 'Tumblr' => 33530,
+ 'Twitch' => 35024,
+ 'Twitter' => 33531,
+ 'Uplay PC' => 34689,
+ 'Viber' => 33532,
+ 'Viewster' => 34326,
+ 'Vimeo' => 33533,
+ 'Volksbank' => 34717,
+ 'Warface' => 37524,
+ 'Warframe' => 37136,
+ 'Waze' => 33534,
+ 'Whatsapp' => 33535,
+ 'Wikipedia' => 33536,
+ 'Willhaben.at' => 35859,
+ 'World of Tanks' => 36674,
+ 'World of Warcraft' => 36998,
+ 'World of Warships' => 38009,
+ 'Xbox Live' => 33538,
+ 'Yahoo Mail' => 33539,
+ 'Yahoo Messenger' => 33540,
+ 'Yesss' => 35346,
+ 'Youtube' => 33541,
+ 'Z1 Battle Royale' => 35489,
+ ),
+ 'Deutschland' => array(
+ '1&1' => 32554,
+ '1blu' => 37319,
+ '2k' => 37731,
+ '3CX' => 36439,
+ '3sat' => 35797,
+ 'Afterbuy' => 37015,
+ 'Airbnb' => 35422,
+ 'Albion Online' => 38799,
+ 'Aldi Talk' => 32579,
+ 'Alexa' => 35912,
+ 'All-inkl' => 35162,
+ 'Amazon' => 32572,
+ 'Amazon Prime Music' => 37584,
+ 'Amazon Prime Video' => 34495,
+ 'Amazon Web Services' => 36326,
+ 'Amino Apps' => 39033,
+ 'Amplus' => 35446,
+ 'Anthem' => 38055,
+ 'Anydesk' => 37487,
+ 'AOL' => 34377,
+ 'Apex Legends' => 38112,
+ 'App Store' => 35579,
+ 'Apple Music' => 35246,
+ 'Apple Store' => 34448,
+ 'Arche NetVision' => 35593,
+ 'ArcheAge' => 35062,
+ 'Arcor' => 34374,
+ 'ARK: Survival Evolved' => 39065,
+ 'Arma 3' => 35063,
+ 'Asana' => 38024,
+ 'Assassin\'s Creed' => 35010,
+ 'Badoo' => 35011,
+ 'Base' => 32568,
+ 'Battlefield' => 36092,
+ 'Baur' => 35043,
+ 'Bet3000' => 35035,
+ 'Bet365' => 35034,
+ 'Bethesda' => 38317,
+ 'BILDmobil' => 32609,
+ 'Binance' => 36942,
+ 'Bing' => 34708,
+ 'Bitfinex' => 36833,
+ 'Bitstamp' => 36808,
+ 'Blackberry' => 3,
+ 'Blade &Soul' => 35512,
+ 'Blau' => 37655,
+ 'Blau' => 34108,
+ 'Blizzard Battle.net' => 34483,
+ 'Blogger' => 32606,
+ 'BMW ConnectedDrive' => 38034,
+ 'Boom Beach' => 34365,
+ 'Bornet' => 34944,
+ 'Bwin' => 34491,
+ 'Call of Duty' => 34155,
+ 'Candy Crush' => 35148,
+ 'Candy Crush Soda Saga' => 35174,
+ 'Car-Net' => 37031,
+ 'Car2Go' => 34555,
+ 'Centurylink' => 35624,
+ 'Checkdomain' => 36096,
+ 'Clash of Clans' => 34289,
+ 'Clash Royale' => 35588,
+ 'Cloudflare' => 34881,
+ 'Coinbase' => 36798,
+ 'Colt' => 37653,
+ 'Comdirect' => 34774,
+ 'Comedy Central' => 34122,
+ 'Commerzbank' => 32607,
+ 'Comunio' => 34719,
+ 'Congstar' => 32590,
+ 'Consors Bank' => 35545,
+ 'CosmosDirect' => 35042,
+ 'Counter-strike' => 34887,
+ 'Crunchyroll' => 36718,
+ 'DABbank' => 35921,
+ 'Das Erste' => 34386,
+ 'Dazn' => 35956,
+ 'Dead By Daylight' => 35951,
+ 'Deezer' => 33831,
+ 'DeGiro' => 38203,
+ 'Deliveroo' => 37546,
+ 'Destiny' => 34895,
+ 'Deutsche Bahn' => 32569,
+ 'Deutsche Bank' => 32611,
+ 'Deutsche Glasfaser' => 36087,
+ 'Deutsche Telefon' => 35851,
+ 'DeutschlandSIM' => 34635,
+ 'DFP' => 35004,
+ 'DHL' => 34896,
+ 'Discord' => 35796,
+ 'DKB' => 32767,
+ 'DNSNET' => 35670,
+ 'DomainFactory' => 37381,
+ 'Dota 2' => 34900,
+ 'dpd' => 36120,
+ 'Dragon Ball' => 36380,
+ 'Drillisch' => 36019,
+ 'Driveclub' => 34928,
+ 'Dropbox' => 32585,
+ 'E-Plus' => 10121,
+ 'EA' => 34497,
+ 'Easybell' => 34370,
+ 'eBay' => 32567,
+ 'Ecotel' => 36794,
+ 'Elite: Dangerous' => 37077,
+ 'Emailn' => 34687,
+ 'Emerion' => 34614,
+ 'Entega' => 37039,
+ 'Epic Games Store' => 38827,
+ 'Escape from Tarkov' => 37977,
+ 'Etoro' => 36965,
+ 'Eurosport Player' => 36559,
+ 'Eventim' => 37621,
+ 'Evernote ' => 36506,
+ 'Ewe TEL' => 33559,
+ 'Facebook' => 32552,
+ 'Facebook Messenger' => 32560,
+ 'Faceit' => 37147,
+ 'Facetime' => 34603,
+ 'Fallout' => 35433,
+ 'Farm Heroes Saga' => 35175,
+ 'Fidor Bank' => 35894,
+ 'Fifa' => 35469,
+ 'Finya' => 37060,
+ 'Fitbit' => 37972,
+ 'Fl!nk' => 35170,
+ 'Flickr' => 32604,
+ 'Fonic' => 32594,
+ 'For Honor' => 35985,
+ 'Fortnite' => 36626,
+ 'Forza' => 37568,
+ 'Freenet' => 34354,
+ 'Friday the 13th The Game' => 37561,
+ 'Fyve' => 34378,
+ 'G-Portal' => 37155,
+ 'Game of war' => 35230,
+ 'Gameduell' => 37566,
+ 'Gardena Smart' => 37350,
+ 'Garmin' => 37049,
+ 'Gears of War' => 35940,
+ 'Gems of war' => 38802,
+ 'Geocaching' => 37178,
+ 'Ghost Recon' => 36001,
+ 'Giropay' => 38204,
+ 'GitHub' => 35348,
+ 'GLS' => 36119,
+ 'Gmail' => 32584,
+ 'GMX' => 32563,
+ 'Go Daddy' => 34874,
+ 'Goneo' => 37576,
+ 'Google' => 32553,
+ 'Google Drive' => 36603,
+ 'Google Hangouts' => 32600,
+ 'Google Kalender' => 38603,
+ 'Google Play' => 32593,
+ 'Gran Turismo' => 36917,
+ 'Grindr' => 35532,
+ 'GTA 5' => 34754,
+ 'Guild Wars 2' => 35061,
+ 'Halo' => 35419,
+ 'Halo Wars' => 36034,
+ 'Harry Potter: Wizards Unite' => 38686,
+ 'Hay Day' => 34366,
+ 'Helinet' => 34959,
+ 'Hermes' => 35196,
+ 'Hetzner ' => 35943,
+ 'Hipchat' => 34869,
+ 'Hitbox.TV' => 35932,
+ 'Hitman' => 35586,
+ 'Homematic' => 36795,
+ 'Hosteurope' => 37958,
+ 'Htp' => 34400,
+ 'Hue' => 37810,
+ 'Hunt: Showdown' => 38787,
+ 'HypoVereinsbank' => 34965,
+ 'iCloud' => 32549,
+ 'ICQ' => 33123,
+ 'Idealo' => 37156,
+ 'iMessage' => 32671,
+ 'Inexio' => 36371,
+ 'ING DiBa' => 35156,
+ 'Ingress' => 35765,
+ 'Innogy Highspeed' => 37459,
+ 'Instagram' => 32599,
+ 'Intercity Express (ICE)' => 32581,
+ 'iTunes' => 32672,
+ 'Jappy' => 32596,
+ 'Jira' => 36066,
+ 'Jobst DSL' => 36727,
+ 'Jodel' => 36793,
+ 'Joyn' => 38604,
+ 'Jurassic World Alive' => 37310,
+ 'K-Classic Mobil' => 33986,
+ 'Kabel eins‎' => 34392,
+ 'Kickbase' => 37451,
+ 'Kicker' => 37450,
+ 'Kicktipp' => 35824,
+ 'Kik' => 33353,
+ 'Klarmobil' => 32605,
+ 'KMS' => 34399,
+ 'Knuddels' => 35865,
+ 'Kraken' => 36749,
+ 'Ladbrokes' => 35161,
+ 'LastPass' => 34780,
+ 'League of Legends' => 34112,
+ 'Lebara' => 35791,
+ 'Line' => 34300,
+ 'LinkedIn' => 32557,
+ 'Lotto24' => 35040,
+ 'Lottohelden' => 36882,
+ 'Lovoo' => 34814,
+ 'Lufthansa' => 32574,
+ 'Lycamobile' => 34939,
+ 'M-net' => 32571,
+ 'Madden' => 38906,
+ 'Mail.de' => 34909,
+ 'Mailbox' => 34832,
+ 'Markt.de' => 37465,
+ 'Maxdome' => 34749,
+ 'MDCC' => 34760,
+ 'MDDSL' => 37056,
+ 'Mercedes Me' => 37153,
+ 'MiCoach' => 34936,
+ 'Microsoft Azure' => 36093,
+ 'Microsoft Teams' => 38185,
+ 'Minecraft' => 32556,
+ 'Mittwald' => 33412,
+ 'Mixer' => 38770,
+ 'Mobilcom Debitel' => 32610,
+ 'MTV' => 34120,
+ 'My Fitness Pal' => 37637,
+ 'Mybet' => 35036,
+ 'N26' => 35719,
+ 'NBA 2k' => 38595,
+ 'Need for Speed' => 35429,
+ 'Netatmo' => 37452,
+ 'Netbeat' => 35906,
+ 'NetCologne' => 32587,
+ 'netcombw' => 35638,
+ 'netcup' => 35632,
+ 'Netflix' => 34630,
+ 'Netkom' => 37201,
+ 'Neverwinter' => 35768,
+ 'Nfon' => 35792,
+ 'Nintendo Network' => 35519,
+ 'Nintendo Switch Online' => 37244,
+ 'Nitrado' => 34941,
+ 'No Man\'s Sky' => 35794,
+ 'NordVPN' => 38584,
+ 'Norisbank' => 34964,
+ 'Nvidia' => 37462,
+ 'Nvidia' => 39069,
+ 'O2' => 10122,
+ 'Office 365' => 34730,
+ 'OkCupid' => 37330,
+ 'OLB' => 37057,
+ 'OneDrive' => 35408,
+ 'Onleihe' => 35635,
+ 'Origin' => 34371,
+ 'Osnatel' => 33873,
+ 'Otelo' => 35480,
+ 'Otto' => 32598,
+ 'Outlook' => 32546,
+ 'Overwatch' => 35684,
+ 'Paladins' => 35925,
+ 'Path of Exile' => 36479,
+ 'Payback' => 37654,
+ 'Paypal' => 34375,
+ 'pcvisit' => 37643,
+ 'PES' => 37952,
+ 'Pet Rescue Saga' => 35176,
+ 'Pinterest' => 37585,
+ 'Placetel' => 35128,
+ 'Playerunknown\'s Battlegrounds' => 36332,
+ 'Playstation Network' => 32551,
+ 'Pokémon Duel' => 35976,
+ 'Pokémon Go' => 35724,
+ 'Pokerstars' => 37439,
+ 'Postbank' => 32589,
+ 'Posteo' => 34309,
+ 'Primacom' => 33502,
+ 'ProSieben' => 34390,
+ 'PŸUR' => 32592,
+ 'QSC' => 33560,
+ 'Quizduell' => 34292,
+ 'Rainbow Six' => 35479,
+ 'Razer' => 38699,
+ 'Realm Royale' => 37288,
+ 'Red Dead Redemption' => 37601,
+ 'Reddit' => 35882,
+ 'RFT Kabel' => 35831,
+ 'Roblox' => 35815,
+ 'Rocket League' => 35252,
+ 'Royal Games' => 38217,
+ 'RTL II' => 34393,
+ 'RTL Television' => 34387,
+ 'Runescape' => 35108,
+ 'RWE' => 36116,
+ 'RWW' => 37955,
+ 'Ryanair' => 37518,
+ 'Salesforce' => 34733,
+ 'Santander Consumer Bank' => 32603,
+ 'Sat.1' => 34389,
+ 'Save.TV' => 37193,
+ 'Sea of Thieves' => 37112,
+ 'Shpock' => 37311,
+ 'Signal' => 37072,
+ 'Simply' => 36376,
+ 'Simquadrat' => 34945,
+ 'Simsme' => 34795,
+ 'Simyo' => 32591,
+ 'Sipgate' => 34127,
+ 'SKL' => 35041,
+ 'Sky' => 32562,
+ 'Sky Ticket' => 35141,
+ 'Skype' => 32561,
+ 'Skype for Business' => 35351,
+ 'Slack' => 35936,
+ 'Smart Hub' => 35181,
+ 'Smite' => 34803,
+ 'Snapchat' => 33377,
+ 'Soundcloud' => 34353,
+ 'Sparda' => 35370,
+ 'Sparkasse' => 32757,
+ 'Speedtest' => 38780,
+ 'Spiegel' => 36050,
+ 'Spotify' => 32564,
+ 'Star Citizen' => 39035,
+ 'Star Wars Battlefront' => 35460,
+ 'Steam' => 32559,
+ 'Strato' => 33413,
+ 'Strava' => 38731,
+ 'Streetspotr' => 34920,
+ 'Summoners War' => 37420,
+ 'SWB' => 34515,
+ 'Tado' => 36634,
+ 'Tango' => 33731,
+ 'Targobank' => 34966,
+ 'Teamspeak' => 33346,
+ 'Teamviewer' => 34344,
+ 'Tele2' => 33503,
+ 'Tele5' => 35727,
+ 'Telegram' => 34229,
+ 'Telekom' => 10117,
+ 'Tellonym' => 37248,
+ 'The Crew 2' => 37252,
+ 'The Division' => 35570,
+ 'The elder scrolls online' => 34480,
+ 'The Simpsons Tapped Out' => 34701,
+ 'Threema' => 34253,
+ 'Tiktok' => 39044,
+ 'Tinder' => 34242,
+ 'Tipico' => 34714,
+ 'TNG' => 38772,
+ 'Todoist' => 36462,
+ 'TomTom' => 35813,
+ 'Tumblr' => 32588,
+ 'TuneIn' => 38763,
+ 'TV Now' => 35143,
+ 'Tweakbox' => 38349,
+ 'Twitch' => 34376,
+ 'Twitter' => 32583,
+ 'Udemy' => 38388,
+ 'Unitymedia' => 32548,
+ 'Uplay PC' => 34380,
+ 'Usenext' => 36117,
+ 'Vero' => 37064,
+ 'Versatel' => 33561,
+ 'Viber' => 33372,
+ 'Viewster' => 34324,
+ 'Vimeo' => 32582,
+ 'Visa' => 37238,
+ 'VIVA' => 34121,
+ 'Vodafone' => 10120,
+ 'Volksbanken und Raiffeisenbanken' => 32758,
+ 'VOX' => 34391,
+ 'Warface' => 35944,
+ 'Warframe' => 36366,
+ 'Watchbox' => 36537,
+ 'Wattpad' => 34700,
+ 'Waze' => 33411,
+ 'Web.de' => 32586,
+ 'WeChat' => 34301,
+ 'Weebly' => 34914,
+ 'Weight Watchers' => 35662,
+ 'WeTransfer' => 36433,
+ 'Wetter.com' => 36051,
+ 'WetterOnline' => 34810,
+ 'Whatsapp' => 32555,
+ 'Wikipedia' => 32565,
+ 'Wilhelm.tel' => 34398,
+ 'Wish' => 38153,
+ 'WiSoTEL' => 37543,
+ 'Wobcom' => 35991,
+ 'Wordpress' => 32570,
+ 'World of Tanks' => 35524,
+ 'World of Warcraft' => 34373,
+ 'World of Warships' => 36638,
+ 'Wüstenrot' => 36977,
+ 'Xbox Live' => 32573,
+ 'Xing' => 34822,
+ 'Yahoo Mail' => 32597,
+ 'Yahoo Messenger' => 32580,
+ 'Yourfone' => 33415,
+ 'Youtube' => 32578,
+ 'Youtube Music' => 37586,
+ 'Z1 Battle Royale' => 35147,
+ 'Zattoo' => 35367,
+ 'ZDF' => 34388,
+ 'Zynga' => 32608,
+ ),
+ 'Nederland' => array(
+ '112' => 10011,
+ '3FM' => 10174,
+ '9292.nl' => 33376,
+ 'ABN-Amro' => 29,
+ 'ABP pensioenfonds' => 35862,
+ 'Adobe Creative Cloud' => 34916,
+ 'ADP' => 32669,
+ 'Adyen' => 37610,
+ 'Aegon Bank' => 10132,
+ 'Afas' => 10093,
+ 'Afterpay' => 34769,
+ 'Airbnb' => 35423,
+ 'Airmiles' => 37516,
+ 'Albert Heijn' => 34010,
+ 'Alex' => 10056,
+ 'Algemeen Dagblad' => 1,
+ 'AliExpress' => 37384,
+ 'Amazon' => 37379,
+ 'Amazon Prime Video' => 36976,
+ 'AMSIX' => 10008,
+ 'Antagonist' => 35160,
+ 'Anthem' => 38054,
+ 'Apex Legends' => 38118,
+ 'App Store' => 35580,
+ 'Apple Music' => 35245,
+ 'Apple Store' => 34446,
+ 'Argenta' => 10158,
+ 'Argeweb' => 35073,
+ 'Arriva' => 2,
+ 'ASN Bank' => 10048,
+ 'Assassin\'s Creed' => 35009,
+ 'Badoo' => 37650,
+ 'Battlefield' => 37094,
+ 'Belastingdienst' => 10002,
+ 'Ben' => 10053,
+ 'Bibliotheek' => 34132,
+ 'Binance' => 36879,
+ 'Binck' => 10055,
+ 'Bing' => 34707,
+ 'BlaBlaCar' => 36088,
+ 'Bliep' => 33998,
+ 'Blizzard Battle.net' => 34485,
+ 'Bol.com' => 10112,
+ 'Booking.com' => 37574,
+ 'Boom Beach' => 34363,
+ 'Brabant Water' => 10071,
+ 'Brawl Stars' => 38818,
+ 'Budgetphone' => 35132,
+ 'Buienalarm' => 37245,
+ 'Buienradar' => 33565,
+ 'Bunq' => 35820,
+ 'Byte' => 32764,
+ 'Caiway' => 4,
+ 'CAK' => 37289,
+ 'Call of Duty' => 34154,
+ 'CanalDigitaal' => 31,
+ 'Candy Crush' => 34025,
+ 'Cbizz' => 37659,
+ 'Centraal Beheer Achmea' => 10157,
+ 'Centraal Bureau voor de Statistiek' => 10168,
+ 'CheapConnect' => 36122,
+ 'Chelloo' => 35546,
+ 'Choozze' => 35096,
+ 'Clash of Clans' => 34290,
+ 'Clash Royale' => 37522,
+ 'Cloudflare' => 38623,
+ 'Cloudhosting.nl' => 33486,
+ 'Coinbase' => 36236,
+ 'Comedy Central' => 34033,
+ 'Concepts' => 10043,
+ 'Connexxion' => 5,
+ 'Coolblue' => 35543,
+ 'Counter-strike' => 36644,
+ 'Credit Europe Bank' => 10194,
+ 'Crunchyroll' => 36722,
+ 'Dead By Daylight' => 37412,
+ 'Deezer' => 33769,
+ 'DeGiro' => 34019,
+ 'Delight Mobile' => 33987,
+ 'Delta' => 10123,
+ 'Destiny' => 34891,
+ 'Deutsche Bank' => 10119,
+ 'DFP' => 35003,
+ 'DHL' => 35223,
+ 'DigiD' => 10001,
+ 'Digipoort' => 34520,
+ 'Discord' => 36043,
+ 'Disney+' => 38319,
+ 'Dota 2' => 36397,
+ 'Dpd' => 35619,
+ 'Dropbox' => 10192,
+ 'Dumpert' => 33375,
+ 'Dunea' => 10074,
+ 'EA' => 34501,
+ 'Easynet' => 33997,
+ 'eBay' => 33857,
+ 'Elite: Dangerous' => 37777,
+ 'Enduris' => 35999,
+ 'Eneco' => 10124,
+ 'Energielabel voor Woningen' => 35117,
+ 'Enexis' => 10014,
+ 'Ennatuurlijk' => 35159,
+ 'Epic Games Store' => 39020,
+ 'Escape from Tarkov' => 39059,
+ 'Esprit Telecom' => 10150,
+ 'Essent' => 10114,
+ 'Etoro' => 36958,
+ 'Eurosport Player' => 35821,
+ 'Eventim' => 37622,
+ 'Evides' => 10072,
+ 'Eweka' => 10039,
+ 'Exact Online' => 34815,
+ 'Exchange Online' => 34728,
+ 'Facebook' => 6,
+ 'Facebook Messenger' => 10185,
+ 'Facetime' => 34607,
+ 'Fallout' => 35434,
+ 'FBTO' => 34015,
+ 'Feedly' => 34712,
+ 'Fiber' => 10103,
+ 'Fifa' => 35474,
+ 'Flickr' => 37948,
+ 'Flitsmeister' => 34369,
+ 'For Honor' => 35987,
+ 'Fortnite' => 36625,
+ 'Fox Sports' => 10096,
+ 'Friday the 13th The Game' => 37560,
+ 'Funda' => 32576,
+ 'Game of war' => 35231,
+ 'Garmin' => 38165,
+ 'Garmin Connect' => 38171,
+ 'Gatehub' => 36957,
+ 'Ghost Recon' => 36010,
+ 'GitHub' => 35347,
+ 'Glashart Media' => 10105,
+ 'GLS' => 36118,
+ 'Gmail' => 10041,
+ 'Google' => 10010,
+ 'Google Agenda' => 38602,
+ 'Google Drive' => 34276,
+ 'Google Hangouts' => 10062,
+ 'Google Play' => 10038,
+ 'Gran Turismo' => 36873,
+ 'Greenchoice' => 37959,
+ 'Greenwheels' => 34007,
+ 'Grindr' => 35531,
+ 'GTA 5' => 34753,
+ 'Guild Wars 2' => 36464,
+ 'GVB' => 7,
+ 'Halo' => 35420,
+ 'Happn' => 37014,
+ 'Harry Potter: Wizards Unite' => 38689,
+ 'Hay Day' => 34368,
+ 'Hearthstone' => 38564,
+ 'Hollandsnieuwe' => 10040,
+ 'Hosted.nl' => 33483,
+ 'Hostnet' => 32761,
+ 'HTM' => 8,
+ 'Hue' => 37812,
+ 'iCloud' => 30,
+ 'iDeal' => 10025,
+ 'IEX' => 35782,
+ 'IG' => 34307,
+ 'iMessage' => 10130,
+ 'Indeed' => 35941,
+ 'Infopact' => 37565,
+ 'ING' => 9,
+ 'Instagram' => 32558,
+ 'International Card Services (ICS)' => 10169,
+ 'InterNLnet' => 34252,
+ 'Interpolis' => 34017,
+ 'ITDev Solutions' => 35533,
+ 'iTunes' => 10151,
+ 'Jira' => 36067,
+ 'Jonaz' => 37348,
+ 'Jumbo' => 36184,
+ 'Jurassic World Alive' => 37334,
+ 'JustEat' => 10164,
+ 'Kabel Noord' => 10113,
+ 'Kabeltex' => 10138,
+ 'Kadaster' => 37652,
+ 'Kamer van Koophandel' => 10167,
+ 'KickXL' => 10098,
+ 'Kik' => 10191,
+ 'Kliksafe' => 10109,
+ 'KLM' => 10028,
+ 'Knab' => 10131,
+ 'KNMI' => 34013,
+ 'KPN' => 11,
+ 'Kraken' => 36748,
+ 'Kruidvat' => 37312,
+ 'LastPass' => 34779,
+ 'League of Legends' => 35169,
+ 'LeasePlan Bank' => 10160,
+ 'Leaseweb' => 32762,
+ 'Lebara' => 10128,
+ 'Lexa.nl' => 35838,
+ 'Liander' => 10013,
+ 'Lijbrandt' => 10045,
+ 'LinkedIn' => 10201,
+ 'Litebit' => 36836,
+ 'Lloyds Bank' => 10154,
+ 'LOI' => 34947,
+ 'Lotto' => 34923,
+ 'Lycamobile' => 10129,
+ 'Lynx' => 10085,
+ 'Magister' => 35274,
+ 'Marktplaats' => 10170,
+ 'Microsoft Azure' => 36114,
+ 'Microsoft Teams' => 38186,
+ 'Mijnbroker' => 10088,
+ 'Mijndomein' => 34348,
+ 'MijnOverheid' => 10015,
+ 'Minecraft' => 36173,
+ 'Mobicross' => 34898,
+ 'Moneyou' => 10155,
+ 'Motto' => 35482,
+ 'MTV' => 34031,
+ 'Multisafepay' => 34877,
+ 'My Fitness Pal' => 37636,
+ 'MyOrder' => 34291,
+ 'Nationale Nederlanden' => 10166,
+ 'Nest' => 35189,
+ 'Net 5' => 10181,
+ 'Netatmo' => 37453,
+ 'Netflix' => 33849,
+ 'Neverwinter' => 36676,
+ 'NIBC Direct' => 10159,
+ 'Nintendo eShop' => 34105,
+ 'Nintendo Network' => 35520,
+ 'Nintendo Switch Online' => 37242,
+ 'Nitrado' => 35549,
+ 'NLE' => 37651,
+ 'NLziet' => 34219,
+ 'NordVPN' => 38585,
+ 'NOS.nl' => 10063,
+ 'NPO 1' => 10179,
+ 'NPO 2' => 10180,
+ 'NPO 3' => 10182,
+ 'NPO Start' => 10064,
+ 'NS' => 21,
+ 'Nu.nl' => 12,
+ 'Nuon' => 10084,
+ 'Oasen' => 10078,
+ 'Office 365' => 35119,
+ 'OHRA' => 34819,
+ 'ON' => 10097,
+ 'OneDrive' => 32779,
+ 'Online.nl' => 10193,
+ 'OnlineWerkplekken.nl' => 33485,
+ 'Onsbrabantnet' => 10044,
+ 'Origin' => 34372,
+ 'Outlook' => 10042,
+ 'OV-chipkaart' => 10145,
+ 'Overwatch' => 35723,
+ 'Paladins' => 37407,
+ 'Park Mobile' => 10139,
+ 'Park-line' => 10137,
+ 'Path of Exile' => 37729,
+ 'Pathé Thuis' => 33848,
+ 'Paypal' => 10021,
+ 'Paysafecard' => 10152,
+ 'PCextreme' => 32763,
+ 'Picnic' => 37503,
+ 'PIN' => 10009,
+ 'Player Unknown\'s Battlegrounds' => 36336,
+ 'Playstation Network' => 10006,
+ 'Plinq' => 10108,
+ 'Pokémon Go' => 35731,
+ 'Pokerstars' => 37438,
+ 'PostNL' => 32766,
+ 'PWN Waterleidingbedrijf Noord-Holland' => 10073,
+ 'Q-Park' => 10111,
+ 'Quizduel' => 34293,
+ 'Qurrent' => 35729,
+ 'Rabobank' => 13,
+ 'Radio 1' => 10175,
+ 'Radio 2' => 10176,
+ 'Raet' => 32670,
+ 'Rainbow Six' => 35564,
+ 'Realm Royale' => 37315,
+ 'Red Dead Redemption' => 38286,
+ 'Reddit' => 36822,
+ 'Redworks' => 34773,
+ 'Reggefiber' => 10104,
+ 'RegioBank' => 10050,
+ 'Rekam' => 10195,
+ 'Rendo Netwerken' => 10126,
+ 'RET' => 14,
+ 'Reviced' => 36061,
+ 'Robeco' => 10153,
+ 'Robin Mobile' => 35695,
+ 'Roblox' => 35814,
+ 'Rocket League' => 35254,
+ 'RoutIT' => 34349,
+ 'RTL 5' => 10183,
+ 'RTL 8' => 10184,
+ 'RTL XL' => 10066,
+ 'RTL4' => 10178,
+ 'Runescape' => 35701,
+ 'Ruzzle' => 33968,
+ 'Ryanair' => 37517,
+ 'Salesforce' => 10016,
+ 'SBS6' => 10177,
+ 'Schiphol' => 10027,
+ 'Scorito' => 34726,
+ 'Sea of Thieves' => 37113,
+ 'SEOshop' => 35592,
+ 'Sharepoint Online' => 34732,
+ 'Signal' => 37073,
+ 'Signet' => 34407,
+ 'Simpel' => 10037,
+ 'Simyo' => 10054,
+ 'Skype' => 10024,
+ 'Skype for Business' => 34729,
+ 'Slack' => 37336,
+ 'Smart Hub' => 35180,
+ 'Snapchat' => 10187,
+ 'Snappet' => 37613,
+ 'SNS' => 10019,
+ 'Sociale Verzekeringsbank (SVB)' => 10186,
+ 'Sofort Banking' => 10149,
+ 'Solcon' => 10099,
+ 'Soundcloud' => 34352,
+ 'Sparql' => 34519,
+ 'Speurders' => 34805,
+ 'Spotify' => 10003,
+ 'Staatsloterij' => 10094,
+ 'Star Wars Battlefront' => 36918,
+ 'Steam' => 34106,
+ 'Stedin' => 10012,
+ 'Steep' => 37823,
+ 'Stemwijzer' => 35980,
+ 'Stichting Kabeltelevisie Pijnacker' => 34143,
+ 'Stipte' => 10102,
+ 'Strato' => 35045,
+ 'Strava' => 36046,
+ 'Studiemeter' => 37075,
+ 'Studystore' => 36600,
+ 'Surfnet' => 34396,
+ 'T-Mobile' => 19,
+ 'Tado' => 36633,
+ 'Tango' => 33740,
+ 'Teamviewer' => 34342,
+ 'Tele2' => 16,
+ 'Telegraaf' => 17,
+ 'Telegram' => 34221,
+ 'Telfort' => 18,
+ 'The Division' => 35569,
+ 'The elder scrolls online' => 37329,
+ 'Threema' => 34254,
+ 'Thuisbezorgd.nl' => 10163,
+ 'Ticketmaster' => 10133,
+ 'Tickney ' => 35923,
+ 'Tikkie' => 36737,
+ 'Tiktok' => 39074,
+ 'Tinder' => 34238,
+ 'Today\'s' => 10087,
+ 'TomTom Live' => 34917,
+ 'Toto' => 35590,
+ 'TradersOnly' => 10090,
+ 'Transavia' => 35168,
+ 'TransIP' => 32771,
+ 'Trined' => 10107,
+ 'Triodos Bank' => 10051,
+ 'True' => 36576,
+ 'Tumblr' => 36714,
+ 'TuneIn' => 38762,
+ 'Tweak' => 10100,
+ 'Tweakbox' => 38348,
+ 'Tweakers' => 37376,
+ 'Twinfield' => 36725,
+ 'Twitch' => 35025,
+ 'Twitter' => 22,
+ 'Unet' => 34408,
+ 'Uplay PC' => 34379,
+ 'UWV en Werk.nl' => 10017,
+ 'Van Lanschot Bankiers' => 10052,
+ 'VDX' => 35780,
+ 'Vectone' => 35237,
+ 'Veolia' => 32612,
+ 'Veronica' => 34493,
+ 'Versio' => 32765,
+ 'VGZ' => 34946,
+ 'Viber' => 10172,
+ 'Videoland' => 33850,
+ 'Vimeo' => 38534,
+ 'Vimexx' => 35924,
+ 'VirtualComputing.nl' => 35698,
+ 'Vitens' => 10070,
+ 'Vodafone' => 24,
+ 'VoIPmobiel' => 34692,
+ 'Volgjezorg' => 37645,
+ 'VPSHosting.nl' => 33487,
+ 'VPSServer.nl' => 33484,
+ 'VVV Cadeaubon' => 35134,
+ 'Warface' => 38764,
+ 'Warframe' => 36490,
+ 'Waterbedrijf Groningen' => 10077,
+ 'Waterleiding Maatschappij Limburg' => 10076,
+ 'Waterleidingmaatschappij Drenthe' => 10079,
+ 'Waternet' => 10075,
+ 'Waze' => 33409,
+ 'Webex' => 34164,
+ 'Webreus' => 32778,
+ 'Weebly' => 34913,
+ 'Weeronline.nl' => 34014,
+ 'Weerplaza' => 35115,
+ 'Wehkamp' => 33980,
+ 'Westland Infra' => 10125,
+ 'WeTransfer' => 10190,
+ 'Whatsapp' => 10000,
+ 'Wikipedia' => 10092,
+ 'Wish' => 38152,
+ 'Wisper' => 10101,
+ 'Woningnet' => 36758,
+ 'Wordfeud' => 25,
+ 'WordOn' => 34036,
+ 'World of Tanks' => 35526,
+ 'World of Warcraft' => 34382,
+ 'World of Warships' => 38010,
+ 'Wrts' => 34215,
+ 'Xbox Live' => 10148,
+ 'XS4ALL' => 26,
+ 'XSyou' => 10106,
+ 'Yahoo Mail' => 34020,
+ 'Yellowbrick' => 10140,
+ 'Youfone' => 10144,
+ 'Yourhosting' => 34360,
+ 'YouTube' => 10005,
+ 'Z1 Battle Royale' => 35495,
+ 'Zalando' => 33981,
+ 'Ziggo' => 28,
+ 'Zilveren Kruis' => 34727,
+ 'Zwitserleven' => 34262,
+ ),
+ 'UK' => array(
+ '123 Reg' => 35870,
+ '1and1' => 34818,
+ '2k' => 36427,
+ '3 (Three)' => 32674,
+ '4chan' => 38596,
+ 'Abebooks' => 36536,
+ 'Adobe Creative Cloud' => 34552,
+ 'Airbnb' => 35424,
+ 'Alexa' => 35911,
+ 'AliExpress' => 39062,
+ 'Amazon' => 32613,
+ 'Amazon Prime Music' => 36426,
+ 'Amazon Prime Video' => 34494,
+ 'Amazon Web Services' => 36327,
+ 'American Express' => 37398,
+ 'Amino Apps' => 38196,
+ 'Ancestry' => 38680,
+ 'Anthem' => 38053,
+ 'Anydesk' => 37489,
+ 'Apex Legends' => 38114,
+ 'App Store' => 35578,
+ 'Apple Music' => 35242,
+ 'Apple Store' => 34454,
+ 'Argos' => 34018,
+ 'ARK: Survival Evolved' => 36551,
+ 'Arlo' => 37076,
+ 'Asana' => 38023,
+ 'Asda' => 37979,
+ 'Ask4' => 34411,
+ 'Assassin\'s Creed' => 35006,
+ 'Autotrader' => 34793,
+ 'Badoo' => 37501,
+ 'Bank of Ireland UK' => 38228,
+ 'Bank of Scotland' => 32692,
+ 'Barclaycard' => 37762,
+ 'Barclays' => 32685,
+ 'Battlefield' => 36585,
+ 'Bet365' => 35030,
+ 'Betfair' => 35031,
+ 'Binance' => 36877,
+ 'Bing' => 33615,
+ 'Bitbucket' => 36683,
+ 'Black Desert Online' => 38492,
+ 'Blizzard Battle.net' => 34487,
+ 'Blogger' => 32617,
+ 'Booking.com' => 38703,
+ 'Boom Beach' => 34783,
+ 'Brawl Stars' => 38819,
+ 'British Airways' => 37644,
+ 'British Gas' => 35653,
+ 'BT' => 32673,
+ 'Bumble' => 36401,
+ 'Bwin' => 34490,
+ 'Cablecom' => 34413,
+ 'Cahoot' => 34826,
+ 'Call of Duty' => 34151,
+ 'Candy Crush' => 35094,
+ 'Capital One' => 37223,
+ 'Car-Net' => 37030,
+ 'Cdkeys' => 37575,
+ 'Centurylink' => 35625,
+ 'CEX' => 34897,
+ 'Channel 4' => 34948,
+ 'Chelsea Building Society' => 38223,
+ 'Clash of Clans' => 34444,
+ 'Clash Royale' => 36856,
+ 'Cloudflare' => 34880,
+ 'CMC Markets' => 37629,
+ 'Coinbase' => 36797,
+ 'Colt Group ' => 35961,
+ 'Conan Exiles' => 38392,
+ 'ConnectWise' => 38469,
+ 'Conventry Building Society' => 38225,
+ 'Counter-strike' => 35057,
+ 'Craigslist' => 32619,
+ 'Crunchyroll' => 36715,
+ 'Daisy' => 34410,
+ 'Danske Bank' => 38227,
+ 'Dark Souls' => 36953,
+ 'Dauntless' => 38541,
+ 'DayZ' => 38781,
+ 'Dazn' => 39010,
+ 'Dead By Daylight' => 36425,
+ 'Deezer' => 33829,
+ 'DeGiro' => 38202,
+ 'Deliveroo' => 37548,
+ 'Demon' => 34412,
+ 'Destiny' => 34893,
+ 'DeviantArt' => 38491,
+ 'DFP' => 34999,
+ 'Discord' => 36020,
+ 'Dota 2' => 35403,
+ 'Driveclub' => 34927,
+ 'Dropbox' => 32620,
+ 'EA' => 34506,
+ 'EA Sports UFC' => 38468,
+ 'Easynet' => 33881,
+ 'eBay' => 32621,
+ 'Eclipse' => 32680,
+ 'EE' => 32661,
+ 'Elite: Dangerous' => 36684,
+ 'Epic Games Store' => 38828,
+ 'Escape from Tarkov' => 38108,
+ 'Etoro' => 36959,
+ 'Etsy' => 36422,
+ 'Eurosport Player' => 35819,
+ 'Evernote' => 34705,
+ 'Exchange Online' => 34536,
+ 'Expedia' => 36421,
+ 'Experian' => 38156,
+ 'Exponential-E' => 34409,
+ 'Facebook' => 32622,
+ 'Facebook Messenger' => 32623,
+ 'Faceit' => 37145,
+ 'Facetime' => 34604,
+ 'Fallout' => 35431,
+ 'Fandom' => 38690,
+ 'Far Cry' => 37176,
+ 'Fasthosts' => 35705,
+ 'Fifa' => 35471,
+ 'Find my iPhone' => 36123,
+ 'First Direct' => 33978,
+ 'First Trust Bank' => 38226,
+ 'Fitbit' => 36630,
+ 'Flickr' => 32624,
+ 'Fling' => 35165,
+ 'For Honor' => 35988,
+ 'Fortnite' => 36624,
+ 'Forza' => 37569,
+ 'Freedompop' => 35639,
+ 'Freesat' => 37594,
+ 'Freeview' => 35771,
+ 'Friday the 13th The Game' => 37563,
+ 'Funimation' => 37745,
+ 'Game of war' => 35229,
+ 'Gamma' => 34899,
+ 'Garmin' => 36990,
+ 'Garmin Connect' => 37192,
+ 'Gears of War' => 35939,
+ 'Ghost Recon' => 36007,
+ 'Giffgaff' => 33985,
+ 'Gigler' => 35790,
+ 'GitHub' => 32625,
+ 'Glide' => 38901,
+ 'Gmail' => 32626,
+ 'Go Daddy' => 34873,
+ 'Google' => 32627,
+ 'Google Calendar' => 38598,
+ 'Google Cloud' => 38536,
+ 'Google Drive' => 34273,
+ 'Google Hangouts' => 32629,
+ 'Google Home' => 36138,
+ 'Google Play' => 32628,
+ 'GoToMeeting' => 36505,
+ 'Gran Turismo' => 36680,
+ 'Great Western Railway' => 37808,
+ 'Grindr' => 35530,
+ 'GTA 5' => 34752,
+ 'Guild Wars 2' => 36407,
+ 'Gumtree' => 32756,
+ 'Halifax' => 32689,
+ 'Halo' => 35451,
+ 'Harry Potter: Wizards Unite' => 38688,
+ 'Hay Day' => 34788,
+ 'Hayu' => 38052,
+ 'Heart Internet' => 37623,
+ 'Hearthstone' => 38563,
+ 'Hermes' => 34949,
+ 'Hipchat' => 34866,
+ 'Hitman' => 36880,
+ 'Hive' => 39072,
+ 'HMRC' => 36961,
+ 'Home telecom' => 35959,
+ 'Hootsuite' => 32630,
+ 'HQ Trivia' => 37161,
+ 'HSBC' => 32686,
+ 'Hue' => 37811,
+ 'Hunt: showdown' => 38823,
+ 'Hyperoptic' => 36520,
+ 'iCloud' => 32663,
+ 'IG' => 37630,
+ 'iMessage' => 32664,
+ 'Imgur' => 32632,
+ 'IMVU' => 37177,
+ 'Indeed' => 38589,
+ 'Instagram' => 32633,
+ 'Internet Movie Database (IMDb)' => 36752,
+ 'Iomart' => 37180,
+ 'iPlayer' => 32755,
+ 'iTunes' => 32665,
+ 'ITV' => 34302,
+ 'Janet' => 35452,
+ 'Jira' => 34871,
+ 'John Lewis' => 36782,
+ 'Jurassic World Alive' => 37332,
+ 'Just Eat' => 36031,
+ 'KC' => 34130,
+ 'Kik' => 33352,
+ 'Kraken' => 36751,
+ 'Ladbrokes' => 35033,
+ 'LastPass' => 34778,
+ 'League of Legends' => 35048,
+ 'LinkedIn' => 32634,
+ 'Litebit' => 36837,
+ 'Lloyds Bank' => 32691,
+ 'M&S Bank' => 35457,
+ 'M24Seven' => 37150,
+ 'Madden' => 38458,
+ 'Mail.com' => 34800,
+ 'Mailbox' => 34836,
+ 'Mailchimp' => 38728,
+ 'Manx Telecom' => 35534,
+ 'Mastercard' => 37250,
+ 'McDonalds app' => 37374,
+ 'Meetup' => 34246,
+ 'Metro Bank' => 34970,
+ 'Microsoft Azure' => 32651,
+ 'Microsoft Teams' => 38184,
+ 'Minecraft' => 32635,
+ 'Mixer' => 38768,
+ 'Monzo' => 37591,
+ 'Moonfruit' => 35456,
+ 'MTV' => 34124,
+ 'Musical.ly' => 37140,
+ 'My Fitness Pal' => 36956,
+ 'My Vue' => 36329,
+ 'Namesco Ltd' => 35900,
+ 'National Lottery' => 34950,
+ 'Nationwide' => 32690,
+ 'NatWest' => 32684,
+ 'NBA 2k' => 37721,
+ 'Nest' => 35192,
+ 'Netflix' => 32636,
+ 'Neverwinter' => 35767,
+ 'NikePlus' => 38783,
+ 'Nintendo eShop' => 34100,
+ 'Nintendo Network' => 35516,
+ 'Nintendo Switch Online' => 37241,
+ 'No Man\'s Sky' => 37405,
+ 'NordVPN' => 38248,
+ 'Now TV' => 34406,
+ 'Nvidia' => 39068,
+ 'O2' => 32660,
+ 'Office 365' => 34538,
+ 'OkCupid' => 37331,
+ 'Omegle' => 39043,
+ 'OneDrive' => 32781,
+ 'Online.net' => 36174,
+ 'ooVoo' => 36586,
+ 'Orange' => 32676,
+ 'Origin' => 36419,
+ 'Origin Broadband' => 36052,
+ 'Outlook' => 32631,
+ 'Overwatch' => 35681,
+ 'OVH' => 36160,
+ 'Paddy Power' => 35032,
+ 'Paladins' => 36377,
+ 'Path of Exile' => 36487,
+ 'Paypal' => 35557,
+ 'PES' => 38590,
+ 'Photobucket' => 32638,
+ 'Pinterest' => 32639,
+ 'Player Unknown\'s Battlegrounds' => 36335,
+ 'Playstation Network' => 32668,
+ 'PlentyOfFish' => 36023,
+ 'Plusnet' => 32683,
+ 'Pokémon Go' => 35730,
+ 'Pokerstars' => 37440,
+ 'Post Office' => 32682,
+ 'Project Online' => 34539,
+ 'ProtonMail' => 38963,
+ 'Quickbooks Online' => 36583,
+ 'Quizup' => 34298,
+ 'Rackspace' => 34610,
+ 'Rainbow Six' => 35476,
+ 'Rakuten TV' => 37597,
+ 'RBS (Royal Bank of Scotland)' => 32688,
+ 'Realm Royale' => 37309,
+ 'Red Dead Redemption' => 37743,
+ 'Redbox' => 38791,
+ 'Reddit' => 34844,
+ 'Relish' => 34797,
+ 'Revolut' => 37365,
+ 'Roblox' => 35786,
+ 'Rocket League' => 35355,
+ 'Royal Mail' => 35776,
+ 'Runescape' => 35107,
+ 'Ruzzle' => 34479,
+ 'Ryanair' => 36003,
+ 'Sagepay' => 36781,
+ 'Sainsbury\'s Bank' => 35116,
+ 'Salesforce' => 38495,
+ 'Santander' => 32687,
+ 'Sarahah' => 36373,
+ 'Scottish Power' => 36041,
+ 'Sea of Thieves' => 37110,
+ 'Sharepoint Online' => 34540,
+ 'Shopify' => 38538,
+ 'Shutterstock' => 37448,
+ 'Signal' => 37070,
+ 'Sky' => 32782,
+ 'Sky Bet' => 35076,
+ 'Skype' => 32640,
+ 'Skype for Business' => 34537,
+ 'Slack' => 35934,
+ 'Slideshare' => 32641,
+ 'Smart Hub' => 35179,
+ 'Smartsheet' => 38723,
+ 'Smile' => 36661,
+ 'Smite' => 35407,
+ 'Snapchat' => 32642,
+ 'Soundcloud' => 36954,
+ 'Sourceforge' => 32643,
+ 'South Western Railway' => 37809,
+ 'Spotify' => 32644,
+ 'Squarespace' => 38784,
+ 'SSE' => 37058,
+ 'Star Citizen' => 39036,
+ 'Star Wars Battlefront' => 35551,
+ 'Starling Bank' => 38719,
+ 'Steam' => 32667,
+ 'Steep' => 37822,
+ 'Strava' => 37046,
+ 'Streamcenter' => 37016,
+ 'Summoners War' => 37419,
+ 'T-Mobile' => 32679,
+ 'Tado' => 36632,
+ 'Talkmobile' => 33988,
+ 'TalkTalk' => 32677,
+ 'Tango' => 33739,
+ 'Teamviewer' => 34615,
+ 'Telegram' => 34222,
+ 'Tesco Bank' => 34969,
+ 'Tesco Broadband' => 34086,
+ 'Tesco Mobile' => 35149,
+ 'The Co-operative Bank' => 34971,
+ 'The Crew 2' => 36555,
+ 'The Division' => 35561,
+ 'The elder scrolls online' => 36400,
+ 'The People\'s Operator' => 35150,
+ 'The Simpsons Tapped out' => 35077,
+ 'Thinkmoney' => 36331,
+ 'Ticketmaster' => 36786,
+ 'Tiktok' => 38726,
+ 'Tinder' => 34240,
+ 'TomTom Live' => 34918,
+ 'Transferwise' => 38565,
+ 'Trove' => 38826,
+ 'TSB Bank' => 33970,
+ 'Tumblr' => 32645,
+ 'TuneIn' => 37973,
+ 'Tweakbox' => 38342,
+ 'Twitch' => 35022,
+ 'Twitter' => 32646,
+ 'Uber' => 37498,
+ 'Uber Eats' => 38271,
+ 'Udemy' => 37717,
+ 'UKfast' => 36838,
+ 'Ulster Bank' => 36071,
+ 'Unibet' => 36055,
+ 'Uplay PC' => 34691,
+ 'UPS' => 38744,
+ 'Viber' => 33349,
+ 'Vimeo' => 32647,
+ 'Virgin Media' => 32675,
+ 'Visa' => 37237,
+ 'Vistaprint' => 35130,
+ 'Vodafone' => 32659,
+ 'Waitrose' => 36964,
+ 'Warface' => 38766,
+ 'Warframe' => 36367,
+ 'Wattpad' => 34696,
+ 'Waze' => 33407,
+ 'Webex' => 34161,
+ 'Weebly' => 38547,
+ 'Weight Watchers' => 35663,
+ 'WeTransfer' => 32648,
+ 'Whatsapp' => 32649,
+ 'Whisper' => 37028,
+ 'Wikipedia' => 32650,
+ 'William Hill' => 35029,
+ 'Wish' => 39040,
+ 'Wix' => 37233,
+ 'Wordpress.com' => 32652,
+ 'World of Tanks' => 35525,
+ 'World of Warcraft' => 35052,
+ 'World of Warships' => 36639,
+ 'WWE Network' => 38085,
+ 'Xbox Live' => 32666,
+ 'Xero' => 37500,
+ 'XLN Telecom' => 33989,
+ 'Yahoo' => 32653,
+ 'Yahoo Mail' => 32654,
+ 'Yahoo Messenger' => 32655,
+ 'Yammer' => 36955,
+ 'Yelp' => 32656,
+ 'Yorkshire Bank' => 34968,
+ 'Yorkshire Building Society' => 38224,
+ 'Youtube' => 32657,
+ 'Youtube Music' => 37587,
+ 'Yubo' => 37246,
+ 'Z1 Battle Royale' => 35490,
+ 'Zen Internet' => 33874,
+ 'ZoHo' => 36039,
+ 'Zone Broadband' => 36994,
+ 'Zoom' => 37946,
+ 'Zynga' => 32658,
+ ),
+ 'United States' => array(
+ '1and1' => 34817,
+ '1Password' => 36441,
+ '2600hertz' => 37692,
+ '2k' => 34768,
+ '4chan' => 37567,
+ '7 Days to Die' => 35947,
+ '8x8' => 34314,
+ 'ABC' => 38902,
+ 'Abebooks' => 36535,
+ 'Absolver' => 37366,
+ 'Access One' => 36063,
+ 'Acorns' => 37647,
+ 'Adams Networks' => 33556,
+ 'Adobe Connect' => 34134,
+ 'Adobe Creative Cloud' => 34551,
+ 'ADP' => 37657,
+ 'ADT' => 38502,
+ 'Adyen' => 37611,
+ 'Agar.io' => 38216,
+ 'Aio Wireless' => 34098,
+ 'Air Canada' => 20003,
+ 'Airbnb' => 34335,
+ 'AireSpring' => 35893,
+ 'Airnow.gov' => 37658,
+ 'Akamai' => 35447,
+ 'Alaska Airlines' => 20004,
+ 'Alaska Communications' => 36040,
+ 'Albion Online' => 38795,
+ 'Alexa' => 35910,
+ 'AliExpress' => 37395,
+ 'Allegiant Air' => 20005,
+ 'Ally' => 34791,
+ 'Amazon' => 20006,
+ 'Amazon Prime Music' => 34710,
+ 'Amazon Prime Video' => 33370,
+ 'Amazon Web Services' => 10147,
+ 'American Airlines' => 20007,
+ 'American Express' => 35958,
+ 'American Messaging' => 34128,
+ 'Amino Apps' => 37290,
+ 'Ammyy' => 36575,
+ 'Amtrak' => 20008,
+ 'Ancestry' => 38296,
+ 'Anno 1800' => 38413,
+ 'Anthem' => 37746,
+ 'Antietam' => 37051,
+ 'Anydesk' => 37406,
+ 'AOL' => 33419,
+ 'Apex Legends' => 38111,
+ 'App Store' => 35575,
+ 'Apple Maps' => 36125,
+ 'Apple Music' => 35241,
+ 'Apple News' => 36126,
+ 'Apple Store' => 34447,
+ 'Apple TV' => 36058,
+ 'Apple TV+' => 38318,
+ 'Appriver' => 37074,
+ 'AppValley' => 37749,
+ 'Arbuckle' => 34489,
+ 'ArcheAge' => 34876,
+ 'ARK: Survival Evolved' => 36350,
+ 'Arlo' => 36779,
+ 'Armstrong' => 34027,
+ 'Arvest Bank' => 37148,
+ 'Arvig' => 34919,
+ 'Asana' => 35828,
+ 'Assassin\'s Creed' => 35005,
+ 'AT&T' => 20010,
+ 'Atlantic Broadband' => 33437,
+ 'Authorize.net' => 34821,
+ 'Autotask' => 37579,
+ 'BabyTEL' => 35631,
+ 'Backblaze' => 35483,
+ 'Badoo' => 35993,
+ 'Bandwidth' => 35667,
+ 'Bank of America' => 20011,
+ 'Barclays' => 37639,
+ 'BART' => 20012,
+ 'Batman The Telltale Series' => 35896,
+ 'Battalion 1944' => 37002,
+ 'Battleborn' => 35718,
+ 'Battlefield' => 36091,
+ 'Battlerite' => 36820,
+ 'BB&T' => 35658,
+ 'Beats Music' => 34294,
+ 'beIN' => 37355,
+ 'Bejeweled' => 35904,
+ 'Bendbroad' => 34884,
+ 'Best Buy' => 34329,
+ 'BET' => 34125,
+ 'Bethesda' => 38316,
+ 'Binance' => 36818,
+ 'Bing' => 20014,
+ 'Birch Communications' => 33549,
+ 'Bitbucket' => 35414,
+ 'Bitfinex' => 36787,
+ 'Bitflyer' => 36789,
+ 'Bitstamp' => 34023,
+ 'Bittrex' => 36788,
+ 'Black Desert Online' => 37108,
+ 'BlackBerry' => 20015,
+ 'Blade and Soul' => 35511,
+ 'Blizzard Battle.net' => 34486,
+ 'Blogger' => 20016,
+ 'Blue Jay Wireless' => 35464,
+ 'Bluebird' => 37362,
+ 'Bluehost' => 33418,
+ 'BlueJeans' => 37509,
+ 'BMW ConnectedDrive' => 38471,
+ 'BNY Mellon' => 35674,
+ 'Boingo' => 37377,
+ 'Booking.com' => 34330,
+ 'Boom Beach' => 34364,
+ 'Box' => 32775,
+ 'Brawl Stars' => 38312,
+ 'BT' => 38338,
+ 'Buckeye Cablesystem' => 34029,
+ 'Buffer' => 36013,
+ 'Bullet Force' => 37109,
+ 'Bumble' => 35823,
+ 'C Spire' => 38219,
+ 'Cable One' => 20019,
+ 'Call of Duty' => 34148,
+ 'CallTower' => 35365,
+ 'Caltrain' => 20021,
+ 'Candy Crush' => 34024,
+ 'Candy Crush Soda Saga' => 35171,
+ 'Canva' => 36778,
+ 'Capital One' => 20022,
+ 'Cash App' => 38685,
+ 'CBSSports' => 35826,
+ 'Century National Bank' => 37690,
+ 'CenturyLink' => 20023,
+ 'Change.org' => 35616,
+ 'Charles Schwab' => 20078,
+ 'Chase' => 20025,
+ 'Chegg' => 36054,
+ 'Chicago Transit Authority' => 20026,
+ 'Chime' => 39050,
+ 'Chrome Web Store' => 34116,
+ 'Cincinnati Bell' => 33422,
+ 'Cirra Networks' => 36357,
+ 'Citi' => 20027,
+ 'Citizens Bank' => 37748,
+ 'Civilization' => 35869,
+ 'Clash of Clans' => 33550,
+ 'Clash Royale' => 35587,
+ 'Classlink' => 36821,
+ 'Clear' => 33423,
+ 'Cloudflare' => 32542,
+ 'Cloudsmith' => 35946,
+ 'Cloudtrax' => 37528,
+ 'CNET' => 33341,
+ 'CNN' => 34141,
+ 'Cogent' => 34026,
+ 'Coinbase' => 36175,
+ 'Comcast' => 20029,
+ 'Comedy Central' => 34126,
+ 'Common App' => 36726,
+ 'Comporium' => 36032,
+ 'Conan Exiles' => 37195,
+ 'Concur' => 36730,
+ 'Confluence' => 37540,
+ 'ConnectWise' => 37493,
+ 'Consolidated' => 34030,
+ 'Consolidated Edison' => 35679,
+ 'Consumer Cellular' => 37761,
+ 'Copy.com' => 34231,
+ 'Coredial' => 35454,
+ 'Costco' => 37061,
+ 'Counter-strike' => 34886,
+ 'Cox' => 20030,
+ 'Crackle' => 35349,
+ 'Craigslist' => 20031,
+ 'Credit One Bank' => 37760,
+ 'Cricket Wireless' => 20032,
+ 'Crown Castle' => 35812,
+ 'Crunchyroll' => 35114,
+ 'Cryptopia' => 36973,
+ 'Dailymotion' => 37598,
+ 'Dark Souls.' => 35710,
+ 'Dauntless' => 37204,
+ 'DayZ' => 37751,
+ 'Dazn' => 37497,
+ 'DC Universe Online' => 37059,
+ 'Dead By Daylight' => 35760,
+ 'Deezer' => 36424,
+ 'Defiance 2050' => 37364,
+ 'Delta Air Lines' => 20033,
+ 'Destiny' => 34761,
+ 'DeviantArt' => 34888,
+ 'Di.fm' => 35645,
+ 'Diablo' => 34385,
+ 'DirecTV' => 20034,
+ 'Directv Now' => 35933,
+ 'Discord' => 35795,
+ 'Dish Network' => 20035,
+ 'Disney World' => 35837,
+ 'Disney+' => 38800,
+ 'Disqus' => 34145,
+ 'Diversity Lottery' => 38472,
+ 'Dlive' => 38470,
+ 'Docker' => 37817,
+ 'Doom' => 35717,
+ 'Doordash' => 37581,
+ 'Dota 2' => 34304,
+ 'Doublelist' => 37580,
+ 'Downforeveryoneorjustme' => 34758,
+ 'Draftkings' => 37036,
+ 'Dragon Ball' => 35858,
+ 'Dramafever' => 36064,
+ 'DreamHost' => 35926,
+ 'Driveclub' => 35891,
+ 'Dropbox' => 20036,
+ 'Duckduckgo' => 35650,
+ 'Duke Energy' => 35871,
+ 'Duolingo' => 35942,
+ 'Dyl' => 37383,
+ 'Dyn' => 35707,
+ 'E-Trade' => 20037,
+ 'EA' => 34499,
+ 'EA Sports UFC' => 35715,
+ 'Eagle Communications ' => 36027,
+ 'Earthlink' => 32776,
+ 'Eatel' => 35448,
+ 'eBay' => 20038,
+ 'Ecobee' => 37163,
+ 'eFax' => 38664,
+ 'Electric Power Board' => 35778,
+ 'Elite: Dangerous' => 36478,
+ 'Ello' => 34906,
+ 'Endicia' => 36839,
+ 'Engine Yard' => 33966,
+ 'eNom' => 35901,
+ 'EPB Chattanooga' => 35513,
+ 'Epic Games Store' => 37756,
+ 'Escape from Tarkov' => 37424,
+ 'ESPN' => 33335,
+ 'ESPN Plus' => 38320,
+ 'Etherdelta' => 36858,
+ 'Etsy' => 33366,
+ 'Eve Online' => 35721,
+ 'Eve Valkyrie' => 35884,
+ 'Evernote' => 34706,
+ 'Everquest' => 38337,
+ 'Exchange Online' => 34534,
+ 'Exede' => 33557,
+ 'Expedia' => 34332,
+ 'Experian' => 38155,
+ 'ExpressVPN' => 37544,
+ 'Faceapp' => 38695,
+ 'Facebook' => 10198,
+ 'Facebook Messenger' => 20039,
+ 'Faceit' => 38543,
+ 'Facetime' => 34606,
+ 'FAFSA' => 37691,
+ 'FairPoint' => 33994,
+ 'Fallout' => 35430,
+ 'Family Search' => 33439,
+ 'Fandango' => 34481,
+ 'Fandom' => 34317,
+ 'Fanduel' => 37035,
+ 'Fanfiction' => 37101,
+ 'Far Cry' => 35713,
+ 'FastMail' => 35779,
+ 'Fatcow' => 34882,
+ 'Fax2mail' => 38665,
+ 'FedEx' => 35843,
+ 'Feedly' => 34704,
+ 'Fidelity' => 36738,
+ 'Fifa' => 35470,
+ 'Final Fantasy' => 35860,
+ 'Find my iPhone' => 38662,
+ 'First Communications ' => 36062,
+ 'FirstEnergy' => 35994,
+ 'FirstLight' => 34879,
+ 'Fitbit' => 35800,
+ 'Fite' => 38794,
+ 'Fiverr' => 37054,
+ 'Flickr' => 20040,
+ 'Fling' => 37353,
+ 'Flipboard' => 33491,
+ 'Florida Power & Light' => 35699,
+ 'Fonality' => 34312,
+ 'For Honor' => 35984,
+ 'Forge Of Empires' => 35886,
+ 'Fortnite' => 36375,
+ 'Forza' => 36817,
+ 'Fox News' => 35880,
+ 'Fox Sports Go' => 37164,
+ 'Frankfort PlantBoard' => 35466,
+ 'Freedompop' => 35657,
+ 'Freepik' => 36739,
+ 'Friday the 13th The Game' => 36348,
+ 'Frii' => 35668,
+ 'Frontier' => 20041,
+ 'Frontier Airlines' => 20042,
+ 'FuboTV' => 36658,
+ 'Funimation' => 36665,
+ 'Fuze' => 35847,
+ 'FXNOW' => 37504,
+ 'G-Portal' => 37154,
+ 'G2A.com' => 35898,
+ 'Game of Thrones Conquest' => 37669,
+ 'Game of war' => 35228,
+ 'Gamebattles' => 37753,
+ 'Gameloft' => 35964,
+ 'Gamestop' => 36780,
+ 'Gang Beasts' => 36926,
+ 'Garmin' => 35554,
+ 'Garmin Connect' => 35801,
+ 'Gatehub' => 36841,
+ 'GCI' => 35633,
+ 'GDAX' => 36791,
+ 'Gears of War' => 35848,
+ 'Geeking' => 37251,
+ 'Gemini' => 36811,
+ 'Gems of war' => 38801,
+ 'Geocaching' => 35770,
+ 'Gfycat' => 38504,
+ 'Ghost' => 38720,
+ 'Ghost Recon' => 36000,
+ 'Ghosttunes' => 34883,
+ 'GitHub' => 10004,
+ 'Gitlab' => 37146,
+ 'Glassdoor' => 35740,
+ 'Glide' => 34016,
+ 'Glitch' => 38721,
+ 'Gmail' => 20043,
+ 'Go Daddy' => 33416,
+ 'GOG.com' => 34287,
+ 'Google' => 10200,
+ 'Google Calendar' => 38597,
+ 'Google Cloud' => 37380,
+ 'Google Drive' => 34271,
+ 'Google Fiber' => 33421,
+ 'Google Hangouts' => 20046,
+ 'Google Home' => 36137,
+ 'Google Play' => 20045,
+ 'GoToMeeting' => 33489,
+ 'Gran Turismo' => 36347,
+ 'Grande' => 34404,
+ 'Greenlight' => 37628,
+ 'Grindr' => 35529,
+ 'Groove Music' => 33972,
+ 'Groupme' => 35739,
+ 'Groupon' => 35709,
+ 'Growtopia' => 36835,
+ 'Grubhub' => 37693,
+ 'GTA 5' => 33995,
+ 'Guild Wars 2' => 35060,
+ 'H&R Block' => 34328,
+ 'Halo' => 35418,
+ 'Halo Wars' => 36035,
+ 'Happn' => 37013,
+ 'Hargray' => 34142,
+ 'Harry Potter: Wizards Unite' => 38593,
+ 'Hashflare' => 37038,
+ 'Hawaiian Airlines' => 20047,
+ 'Hawaiian Telcom' => 33436,
+ 'Hay Day' => 34367,
+ 'Hayu' => 37198,
+ 'HBO Go' => 34340,
+ 'HBO Now' => 38697,
+ 'Healthcare.gov' => 34011,
+ 'Hearthstone' => 36834,
+ 'Heartland' => 38803,
+ 'Heroku' => 33965,
+ 'HiDive' => 37527,
+ 'HInge' => 37625,
+ 'Hipchat' => 34865,
+ 'HitBTC' => 36925,
+ 'Hitman' => 35585,
+ 'Hive' => 37571,
+ 'Honeywell' => 38110,
+ 'Hootsuite' => 20048,
+ 'Hostgator' => 33417,
+ 'Hostmonster' => 35931,
+ 'Hotels.com' => 34334,
+ 'Hotwire' => 34331,
+ 'HouseParty' => 37356,
+ 'HQ Trivia' => 36815,
+ 'HSBC' => 35673,
+ 'Hue' => 37514,
+ 'HughesNet' => 32787,
+ 'Hulu' => 33331,
+ 'Humanity' => 36735,
+ 'Hunt: showdown' => 37006,
+ 'Hurricane Electric' => 35811,
+ 'I3 Broadband' => 36286,
+ 'IBM Cloud' => 37649,
+ 'iCloud' => 20049,
+ 'ICQ' => 34766,
+ 'iFunny' => 38294,
+ 'IGTV' => 37317,
+ 'iHeartRadio‎' => 33369,
+ 'Illinois Century Network' => 36086,
+ 'IMDb Freedrive' => 37960,
+ 'iMessage' => 20050,
+ 'Imgur' => 20051,
+ 'IMVU' => 36523,
+ 'Inbox' => 34318,
+ 'inContact' => 35836,
+ 'Indeed' => 35864,
+ 'Ingress' => 35764,
+ 'Injustice 2' => 36526,
+ 'Inmotion' => 34759,
+ 'Instagram' => 20052,
+ 'Integra' => 33554,
+ 'Interactive Brokers' => 34115,
+ 'Intermedia' => 33973,
+ 'Internet Movie Database (IMDb)' => 33337,
+ 'Intralinks' => 38667,
+ 'Ipage' => 35659,
+ 'iRacing' => 35957,
+ 'Iridium' => 35652,
+ 'Ironsight' => 37142,
+ 'IRS' => 35542,
+ 'iTunes' => 20053,
+ 'iTunes Connect' => 36489,
+ 'iTunes Match' => 36059,
+ 'iWork' => 36124,
+ 'Jabber' => 36524,
+ 'Jackbox' => 38790,
+ 'JetBlue Airways' => 20054,
+ 'Jira' => 34870,
+ 'Jive' => 35453,
+ 'JP Morgan' => 37034,
+ 'Juno' => 32786,
+ 'Jurassic World Alive' => 37256,
+ 'Kayak' => 34338,
+ 'Keek' => 33770,
+ 'Kik' => 32770,
+ 'Kraken' => 36660,
+ 'Kucoin' => 36962,
+ 'last.fm' => 35634,
+ 'LastPass' => 35541,
+ 'LawBreakers' => 36527,
+ 'Layer3 TV' => 37378,
+ 'Leaco' => 35665,
+ 'League of Legends' => 34111,
+ 'Lifesize' => 37003,
+ 'Lightpath' => 35685,
+ 'Limebike' => 37205,
+ 'Limelight Networks' => 35462,
+ 'Line' => 33738,
+ 'LinkedIn' => 20055,
+ 'Linode' => 35907,
+ 'Liquid Web' => 34825,
+ 'LiveLeak' => 38273,
+ 'Liveperson' => 35417,
+ 'Logix' => 38295,
+ 'Logmein' => 33488,
+ 'Lola Wireless' => 35905,
+ 'Lowe\'s' => 38297,
+ 'LS Networks' => 35703,
+ 'Lumos Networks' => 34217,
+ 'Lyft' => 36571,
+ 'Lynda' => 35781,
+ 'Madden' => 37747,
+ 'Maguss' => 37047,
+ 'Mail.com' => 34798,
+ 'Mailbox' => 34831,
+ 'Mailchimp' => 36017,
+ 'MARTA' => 20056,
+ 'Marvel' => 38792,
+ 'Marvel Contest of Champions' => 37005,
+ 'Maryland Transit Administration (MTA)' => 20017,
+ 'Mass Effect ' => 36057,
+ 'Mastercard' => 37249,
+ 'MaxxSouth ' => 36095,
+ 'MBTA' => 20057,
+ 'McDonalds app' => 36369,
+ 'Media Temple' => 35950,
+ 'Mediacom' => 20058,
+ 'Meetme' => 37042,
+ 'Meetup' => 34245,
+ 'Megapath' => 33420,
+ 'Merrill Lynch' => 37032,
+ 'Metra' => 20059,
+ 'Metro PCS' => 20060,
+ 'MetroCast' => 34405,
+ 'Metrolink' => 20061,
+ 'Metronetinc' => 35890,
+ 'MHz Choice' => 37297,
+ 'Miami Dade Transit' => 20062,
+ 'Microsoft Azure' => 32547,
+ 'Microsoft Teams' => 38018,
+ 'Microsoft VLSC' => 38187,
+ 'Midcontinent Media' => 33552,
+ 'Mimecast' => 35783,
+ 'Minecraft' => 20063,
+ 'Mint' => 36589,
+ 'MintSim' => 36438,
+ 'Mitel' => 36005,
+ 'Mixer' => 36525,
+ 'MLB The Show' => 35711,
+ 'MLB TV' => 35712,
+ 'Mobile legends' => 37394,
+ 'Mobile Strike' => 36476,
+ 'Momentum Telecom' => 36733,
+ 'Moneylion' => 38303,
+ 'Monster Hunter' => 37007,
+ 'Mordhau' => 38497,
+ 'Moviepass' => 37004,
+ 'Movies Anywhere' => 38771,
+ 'MovieTickets' => 36178,
+ 'MSL Live' => 37107,
+ 'MTV' => 34133,
+ 'MU Legend' => 36792,
+ 'Music Unlimited' => 35909,
+ 'Musical.ly' => 36659,
+ 'My Fitness Pal' => 35803,
+ 'My Social Security' => 37627,
+ 'Naruto-Storm' => 35845,
+ 'National Grid NY' => 36024,
+ 'NBA 2k' => 35714,
+ 'NBC Sports Live Extra' => 34295,
+ 'NBCNews.com' => 33340,
+ 'NCTC' => 36344,
+ 'Need for Speed' => 35428,
+ 'NEMR' => 35514,
+ 'Nest' => 35190,
+ 'Net10 Wireless' => 34090,
+ 'netBlazr' => 35656,
+ 'Neteller' => 38321,
+ 'Netflix' => 20065,
+ 'Netsuite' => 35743,
+ 'Nettalk' => 36732,
+ 'Network Solutions' => 33548,
+ 'NetZero' => 32785,
+ 'Neverwinter' => 35603,
+ 'New Jersey Transit' => 20066,
+ 'New York MTA' => 20067,
+ 'New York Times' => 33339,
+ 'Newegg' => 35438,
+ 'NewWave Communications' => 36026,
+ 'Nextiva' => 34850,
+ 'NFL Network' => 36572,
+ 'NHL.tv' => 36816,
+ 'Nicehash' => 37037,
+ 'NikePlus' => 35805,
+ 'Nintendo eShop' => 34099,
+ 'Nintendo Network' => 35515,
+ 'Nintendo Switch Online' => 37240,
+ 'No Man\'s Sky' => 35793,
+ 'NordVPN' => 37545,
+ 'North State' => 36840,
+ 'Northland Communications' => 38035,
+ 'Norwood Light' => 35738,
+ 'NTT Communications' => 35856,
+ 'NuGet' => 36740,
+ 'Oculus' => 38253,
+ 'Office 365' => 34532,
+ 'OkCupid' => 35902,
+ 'Okta' => 35742,
+ 'Omegle' => 36522,
+ 'OneDrive' => 32780,
+ 'Onelogin' => 38439,
+ 'Ooma' => 35628,
+ 'ooVoo' => 34085,
+ 'Opera' => 38406,
+ 'Optimum / Cablevision' => 20020,
+ 'OptionsHouse' => 20068,
+ 'optionsXpress' => 20069,
+ 'Oracle Cloud' => 38033,
+ 'Orbitz' => 34337,
+ 'Origin' => 34113,
+ 'OS X Update' => 36127,
+ 'Outlook' => 10205,
+ 'Overdrive' => 35855,
+ 'Overwatch' => 35680,
+ 'Pacific Northern Gas ' => 35807,
+ 'Page Plus' => 34012,
+ 'Pagely' => 33974,
+ 'Paladins' => 35857,
+ 'Pandora' => 20070,
+ 'Paperspace' => 37200,
+ 'Paragon' => 36359,
+ 'PATCO' => 20071,
+ 'PATH' => 20072,
+ 'Path of Exile' => 34823,
+ 'Patreon' => 38503,
+ 'Paypal' => 20073,
+ 'pCloud' => 36588,
+ 'PenTeleData' => 34401,
+ 'Periscope' => 35595,
+ 'Personal Capital' => 36969,
+ 'PES' => 37951,
+ 'PG&E' => 35677,
+ 'PGA Tour Live' => 37235,
+ 'Phonepower' => 35361,
+ 'Photobucket' => 20074,
+ 'Pinterest' => 20075,
+ 'Planetside2' => 35787,
+ 'Player Unknown\'s Battlegrounds' => 36135,
+ 'Playstation Network' => 20076,
+ 'Playstation Vue' => 35188,
+ 'PlentyOfFish' => 35799,
+ 'Plex' => 35573,
+ 'PNC' => 33333,
+ 'Pokémon Duel' => 35966,
+ 'Pokémon Go' => 35725,
+ 'Pokerstars' => 38749,
+ 'Poloniex' => 36349,
+ 'Postmates' => 36774,
+ 'Powerschool' => 35867,
+ 'Prey' => 37295,
+ 'Priceline' => 34333,
+ 'Project Online' => 34535,
+ 'Proofpoint' => 38666,
+ 'ProtonMail' => 36136,
+ 'Quake Champions' => 36773,
+ 'Quickbooks Online' => 35761,
+ 'Quicken' => 36614,
+ 'Quizlet' => 34322,
+ 'Quizup' => 34296,
+ 'Quora' => 34341,
+ 'Rabb.it' => 36819,
+ 'Rackspace' => 34609,
+ 'Rain World Game' => 36042,
+ 'Rainbow Six' => 35463,
+ 'Razer' => 38698,
+ 'RCN' => 32784,
+ 'Realm Royale' => 37287,
+ 'Red Dead Redemption' => 37600,
+ 'Redbox' => 37213,
+ 'Reddit' => 33342,
+ 'Reflexion' => 38733,
+ 'RingCentral' => 34311,
+ 'Rise Broadband' => 35458,
+ 'Robinhood' => 35706,
+ 'Roblox' => 34820,
+ 'Rocket League' => 35251,
+ 'RocketRez' => 35784,
+ 'Roku' => 37194,
+ 'Royal Games' => 38218,
+ 'Runescape' => 34804,
+ 'Runkeeper' => 35802,
+ 'Runtastic' => 35804,
+ 'Rust' => 37755,
+ 'Ruzzle' => 33969,
+ 'Safelink Wireless' => 35467,
+ 'Safenet' => 37538,
+ 'Salesforce' => 32773,
+ 'Santander Bank' => 38656,
+ 'Sarahah' => 36365,
+ 'Schooldesk' => 35468,
+ 'Scottrade' => 20079,
+ 'ScreenConnect' => 35661,
+ 'Scum' => 37464,
+ 'Sea of Thieves' => 36995,
+ 'SEC Network' => 37757,
+ 'Secom' => 36972,
+ 'Second Life' => 37612,
+ 'SEPTA' => 20080,
+ 'Service Electric' => 33553,
+ 'Sharebuilder' => 20081,
+ 'Sharefile' => 37513,
+ 'Sharepoint Online' => 34533,
+ 'Shentel' => 35666,
+ 'Shopify' => 37555,
+ 'Shoretel' => 35846,
+ 'Showtime Anytime' => 35591,
+ 'Shutterstock' => 35704,
+ 'Signal' => 37071,
+ 'SignupGenius' => 35636,
+ 'Simple' => 34790,
+ 'Simple Mobile' => 33979,
+ 'Siri' => 38339,
+ 'SiriusXM' => 37048,
+ 'Skillshare' => 35775,
+ 'Skrill' => 37257,
+ 'Skype' => 20082,
+ 'Skype for Business' => 35350,
+ 'Skyscanner' => 38645,
+ 'SkySwitch' => 36664,
+ 'SkyWest' => 20084,
+ 'Slack' => 35437,
+ 'Slashdot' => 36615,
+ 'Sleeper' => 37455,
+ 'Slideshare' => 20085,
+ 'Sling' => 35155,
+ 'Smart Hub' => 35178,
+ 'Smartsheet' => 38310,
+ 'SmartThings' => 37102,
+ 'Smite' => 34802,
+ 'SNAP EBT' => 34006,
+ 'Snapchat' => 20086,
+ 'Socket' => 37411,
+ 'Sonic.net' => 34403,
+ 'Soundcloud' => 34351,
+ 'Sourceforge' => 20087,
+ 'South Central Communications' => 35759,
+ 'Southern California Edison' => 35700,
+ 'Southwest Airlines' => 20088,
+ 'Spectrum' => 20024,
+ 'Speedtest' => 37354,
+ 'Spirit Communications' => 35808,
+ 'SplashID' => 35594,
+ 'Spotify' => 20090,
+ 'Sprint' => 20091,
+ 'Square' => 37053,
+ 'Squarespace' => 36573,
+ 'Stack Exchange' => 34319,
+ 'Stackoverflow' => 34258,
+ 'Stadia' => 38302,
+ 'Staminus' => 34608,
+ 'Stamps.com' => 36662,
+ 'Star Citizen' => 36477,
+ 'Star Wars Battlefront' => 35459,
+ 'Starbucks' => 37210,
+ 'Starz' => 38291,
+ 'Steam' => 20092,
+ 'Steep' => 36011,
+ 'Straight Talk' => 34097,
+ 'Strava' => 36047,
+ 'Streamlabs' => 37206,
+ 'Strife' => 35853,
+ 'Stripe' => 38668,
+ 'Suddenlink' => 20093,
+ 'Suitebox' => 37211,
+ 'Summit Broadband' => 35617,
+ 'Summoners War' => 37409,
+ 'SunTrust Bank' => 37346,
+ 'Surfline' => 36341,
+ 'SurveyMonkey' => 35963,
+ 'T-Mobile' => 20097,
+ 'T. Rowe Price' => 37033,
+ 'Talkray' => 34750,
+ 'Tango' => 33728,
+ 'Target' => 34320,
+ 'Taxslayer' => 36018,
+ 'TD Ameritrade' => 20094,
+ 'TD Bank' => 35672,
+ 'TDS Telecom' => 33558,
+ 'Teamviewer' => 34343,
+ 'Tekken' => 37196,
+ 'Telecharge' => 37220,
+ 'Telegram' => 34227,
+ 'Tennis TV' => 37040,
+ 'TERA' => 37105,
+ 'Tesla' => 37152,
+ 'The Crew 2' => 35809,
+ 'The Culling' => 37752,
+ 'The Division' => 35558,
+ 'The elder scrolls online' => 35535,
+ 'The Huffington Post' => 33334,
+ 'The Simpsons Tapped out' => 34702,
+ 'The Weather Channel' => 33336,
+ 'Thingiverse' => 38732,
+ 'Threads' => 38983,
+ 'Threema' => 35892,
+ 'TIAA ' => 35597,
+ 'Ticketmaster' => 36534,
+ 'Tidal' => 37512,
+ 'Tiktok' => 38367,
+ 'Tinder' => 34237,
+ 'Titanfall' => 35897,
+ 'Tivo' => 37001,
+ 'Todoist' => 36461,
+ 'Toggl' => 36993,
+ 'TPx Communications' => 34402,
+ 'TracFone Wireless' => 20099,
+ 'Tradeking' => 33768,
+ 'TradeSatoshi' => 37106,
+ 'TradeStation' => 20100,
+ 'Transferwise' => 37199,
+ 'Travelocity' => 34336,
+ 'Trello' => 34796,
+ 'Trove' => 35363,
+ 'Trusted Id' => 36636,
+ 'TSYS' => 36517,
+ 'Tumblr' => 20101,
+ 'TuneIn' => 35221,
+ 'TurboTax' => 34327,
+ 'TV Time' => 37197,
+ 'TW Telecom' => 32783,
+ 'Tweakbox' => 37750,
+ 'Tweetdeck' => 39009,
+ 'Twitch' => 34308,
+ 'Twitter' => 10204,
+ 'Uber' => 36570,
+ 'Uber Eats' => 37648,
+ 'Udacity' => 35842,
+ 'Udemy' => 35644,
+ 'UFC' => 36736,
+ 'UMG Gaming' => 36528,
+ 'Uncharted' => 35716,
+ 'United Airlines' => 20104,
+ 'Untappd' => 37363,
+ 'Uplay PC' => 34381,
+ 'UPS' => 34321,
+ 'Upwork' => 35436,
+ 'US Bank' => 20106,
+ 'US Cellular' => 20103,
+ 'USA Mobility' => 34129,
+ 'USPS' => 34259,
+ 'Utah Broadband' => 36342,
+ 'Vainglory' => 37203,
+ 'Vanguard' => 37011,
+ 'Vectren' => 35872,
+ 'Venmo' => 37209,
+ 'Verizon' => 20107,
+ 'Vero' => 37062,
+ 'Viaero' => 37508,
+ 'Viasat' => 38298,
+ 'Viber' => 32769,
+ 'Viewster' => 34323,
+ 'Viki' => 36065,
+ 'Vimeo' => 20110,
+ 'Vine' => 33368,
+ 'Virgin Mobile' => 34724,
+ 'Visa' => 37239,
+ 'Visible' => 38605,
+ 'Visual Studio Team Services' => 37463,
+ 'Vlive' => 36574,
+ 'Vonage' => 34315,
+ 'Voxer' => 33492,
+ 'VRChat' => 36991,
+ 'VRV' => 36640,
+ 'Vudu' => 34109,
+ 'Vyve Broadband' => 36012,
+ 'W3Schools' => 35887,
+ 'Waiter.com' => 36776,
+ 'Walmart Family' => 35465,
+ 'Walmart.com' => 33338,
+ 'War Thunder' => 37318,
+ 'Warface' => 37510,
+ 'Warframe' => 35825,
+ 'Washington Metropolitan Area Transit Authority' => 20111,
+ 'Wattpad' => 34693,
+ 'Wave Broadband' => 34028,
+ 'Waze' => 33382,
+ 'Webassign' => 35873,
+ 'Webex' => 33490,
+ 'Webhosting.net' => 35435,
+ 'Webs' => 35895,
+ 'Weebly' => 34910,
+ 'Weight Watchers' => 35646,
+ 'Wells Fargo' => 20112,
+ 'Wemo' => 37593,
+ 'Westman' => 35359,
+ 'WeTransfer' => 20113,
+ 'Whatsapp' => 10136,
+ 'Whisper' => 36881,
+ 'Wikipedia' => 20115,
+ 'Wilcoinc' => 35696,
+ 'Wildstar' => 36475,
+ 'William Hill' => 38900,
+ 'Windstream' => 20117,
+ 'Wish' => 38154,
+ 'Wix' => 35596,
+ 'Wordpress.com' => 20118,
+ 'Workday' => 37314,
+ 'World of Tanks' => 35357,
+ 'World of Warcraft' => 34263,
+ 'World of Warships' => 36637,
+ 'World War 3' => 37599,
+ 'World War Z' => 38405,
+ 'WOW' => 20114,
+ 'WP Engine' => 33975,
+ 'Wunderground' => 35948,
+ 'Wunderlist' => 35839,
+ 'WWE Network' => 36056,
+ 'Xbox Live' => 20119,
+ 'Xfinity Flex' => 38412,
+ 'XO' => 32777,
+ 'Yahoo' => 10203,
+ 'Yahoo Mail' => 20120,
+ 'Yahoo Messenger' => 20121,
+ 'Yammer' => 35559,
+ 'Yelp' => 20122,
+ 'Youtube' => 34651,
+ 'Youtube Music' => 37461,
+ 'Youtube TV' => 37296,
+ 'Yubo' => 37720,
+ 'Z1 Battle Royale' => 35146,
+ 'Zayo' => 35866,
+ 'Zelle' => 38683,
+ 'Zendesk' => 35854,
+ 'Zillow' => 33367,
+ 'ZoHo' => 34144,
+ 'Zoom' => 37349,
+ 'Zwift' => 38167,
+ 'Zynga' => 20123,
+ ),
+ 'New Zealand' => array(
+ '2degrees' => 33886,
+ '4chan' => 38270,
+ 'Alexa' => 36920,
+ 'Amurit.net' => 37710,
+ 'Anthem' => 38210,
+ 'ANZ' => 33888,
+ 'Apex Legends' => 38134,
+ 'Apple Store' => 34457,
+ 'ASB' => 33905,
+ 'beIN' => 38493,
+ 'Bigpipe' => 37704,
+ 'Bing' => 33889,
+ 'Blizzard Battle.net' => 38465,
+ 'BNZ' => 33907,
+ 'Call of Duty' => 34150,
+ 'CallPlus' => 33885,
+ 'CCL' => 37705,
+ 'Counter-strike' => 36854,
+ 'Crunchyroll' => 38146,
+ 'Cryptopia' => 36963,
+ 'Dead By Daylight' => 37434,
+ 'Destiny' => 38942,
+ 'Discord' => 38609,
+ 'Dota 2' => 36415,
+ 'EA' => 34505,
+ 'eBay' => 33891,
+ 'Evernote' => 35914,
+ 'Facebook' => 33892,
+ 'Facebook Messenger' => 33893,
+ 'Facetime' => 34587,
+ 'Fifa' => 38400,
+ 'Flip' => 37706,
+ 'Fortnite' => 36655,
+ 'Gmail' => 33894,
+ 'Google' => 33895,
+ 'Google Drive' => 36759,
+ 'Google Hangouts' => 33896,
+ 'Google Play' => 38525,
+ 'Gran Turismo' => 36948,
+ 'Grindr' => 38402,
+ 'GTA 5' => 37277,
+ 'iCloud' => 33921,
+ 'iMessage' => 33922,
+ 'Inspire Net' => 35445,
+ 'Instagram' => 33915,
+ 'iTunes' => 33923,
+ 'Kik' => 33914,
+ 'Kiwibank' => 33906,
+ 'League of Legends' => 38692,
+ 'Lightbox' => 35504,
+ 'LinkedIn' => 33897,
+ 'Minecraft' => 38617,
+ 'My Fitness Pal' => 37635,
+ 'myob' => 38926,
+ 'MyRepublic' => 34931,
+ 'NBA 2k' => 38785,
+ 'Neon' => 37707,
+ 'Netflix' => 34857,
+ 'Nzdating' => 37708,
+ 'Office 365' => 37171,
+ 'OneDrive' => 36863,
+ 'Orcon' => 33883,
+ 'Origin' => 36887,
+ 'Outlook' => 33918,
+ 'Overwatch' => 36416,
+ 'Pandora' => 33919,
+ 'Pinterest' => 33898,
+ 'Player Unknown\'s Battlegrounds' => 36362,
+ 'Playstation Network' => 34858,
+ 'Pokémon Go' => 35733,
+ 'Rabodirect' => 34980,
+ 'Rainbow Six' => 36610,
+ 'Reddit' => 34860,
+ 'Roblox' => 37662,
+ 'Skinny' => 37709,
+ 'Sky TV' => 33887,
+ 'Skype' => 33912,
+ 'Slingshot' => 34737,
+ 'Snapchat' => 33908,
+ 'Spark' => 33884,
+ 'Spotify' => 33910,
+ 'Steam' => 34225,
+ 'Tinder' => 34859,
+ 'Trade Me' => 33916,
+ 'Trustpower' => 37703,
+ 'Twitch' => 36540,
+ 'Twitter' => 33899,
+ 'Viber' => 33909,
+ 'Vodafone' => 33882,
+ 'Voxer' => 33913,
+ 'Wattpad' => 34697,
+ 'WeChat' => 33920,
+ 'Westpac' => 33900,
+ 'Whatsapp' => 33917,
+ 'Wikipedia' => 33901,
+ 'World of Warcraft' => 38814,
+ 'Xbox Live' => 34284,
+ 'Xero' => 35929,
+ 'Yahoo' => 33902,
+ 'Yahoo Mail' => 33903,
+ 'Youtube' => 33904,
+ 'Z1 Battle Royale' => 37266,
+ ),
+ 'België' => array(
+ '2dehands.be' => 34257,
+ 'Apex Legends' => 38141,
+ 'App Store' => 38555,
+ 'Apple Store' => 38925,
+ 'Argenta' => 32491,
+ 'Bancontact Mister Cash' => 33976,
+ 'Base' => 10207,
+ 'Battlefield' => 38444,
+ 'Belfius' => 32545,
+ 'Binance' => 36934,
+ 'Binck' => 32388,
+ 'Blizzard Battle.net' => 38810,
+ 'BNP Paribas Fortis' => 32543,
+ 'Bolero' => 37619,
+ 'Bpost' => 37157,
+ 'Bwin' => 34872,
+ 'Call of Duty' => 35536,
+ 'Clash Royale' => 38948,
+ 'Counter-strike' => 38245,
+ 'Crelan' => 37614,
+ 'Dead By Daylight' => 37445,
+ 'Deezer' => 33828,
+ 'Destiny' => 38559,
+ 'Deutsche Bank' => 34140,
+ 'Discord' => 37391,
+ 'Dommel' => 33977,
+ 'Dota 2' => 38478,
+ 'Dropbox' => 32525,
+ 'EA' => 34841,
+ 'eBay' => 33858,
+ 'EDPnet' => 32855,
+ 'Engie Electrabel' => 37616,
+ 'Epic Games Store' => 39027,
+ 'Facebook' => 22339,
+ 'Facebook Messenger' => 34851,
+ 'Facetime' => 34605,
+ 'Fifa' => 36906,
+ 'Fintro' => 37617,
+ 'Fluvius' => 37615,
+ 'Fortnite' => 36696,
+ 'Ghost Recon' => 39001,
+ 'Gmail' => 32374,
+ 'Google' => 32343,
+ 'Google Hangouts' => 32395,
+ 'Google Play' => 32371,
+ 'Gran Turismo' => 36913,
+ 'Grindr' => 38743,
+ 'GTA 5' => 35500,
+ 'Guild Wars 2' => 36474,
+ 'iCloud' => 22363,
+ 'iMessage' => 32463,
+ 'ING' => 22342,
+ 'Instagram' => 34286,
+ 'Isabel' => 34004,
+ 'Itsme' => 37454,
+ 'iTunes' => 32484,
+ 'Jim Mobile' => 37618,
+ 'KBC' => 32544,
+ 'Kik' => 32524,
+ 'Kraken' => 36828,
+ 'League of Legends' => 38631,
+ 'Lebara' => 32461,
+ 'LinkedIn' => 32534,
+ 'Lycamobile' => 32462,
+ 'Mobile Vikings' => 32854,
+ 'Moneyou' => 32488,
+ 'Multisafepay' => 34878,
+ 'Nest' => 38517,
+ 'Netflix' => 34629,
+ 'Numéricable' => 32856,
+ 'Office 365' => 36409,
+ 'OneDrive' => 35410,
+ 'Orange' => 10208,
+ 'Origin' => 36888,
+ 'Outlook' => 32375,
+ 'Overwatch' => 36383,
+ 'OVH' => 36746,
+ 'Paypal' => 32354,
+ 'Paysafecard' => 32485,
+ 'Play Sports' => 37582,
+ 'Player Unknown\'s Battlegrounds' => 36568,
+ 'Playstation Network' => 32339,
+ 'Pokémon Go' => 35736,
+ 'Proximus' => 10206,
+ 'Rainbow Six' => 36180,
+ 'Reddit' => 37474,
+ 'Roblox' => 38757,
+ 'Rocket League' => 35978,
+ 'Runescape' => 38654,
+ 'Salesforce' => 32349,
+ 'Scarlet' => 32435,
+ 'Simyo' => 32387,
+ 'Skype' => 32357,
+ 'Smartschool' => 37620,
+ 'Snapchat' => 32520,
+ 'Sofort Banking' => 32482,
+ 'Spotify' => 32336,
+ 'Steam' => 34278,
+ 'Strava' => 38161,
+ 'Teamviewer' => 34907,
+ 'Telegram' => 35971,
+ 'Telenet' => 10196,
+ 'Tinder' => 35499,
+ 'TuneIn' => 38759,
+ 'TV Vlaanderen' => 22364,
+ 'Tweakbox' => 38786,
+ 'Twitch' => 36542,
+ 'Twitter' => 22355,
+ 'Unibet' => 38830,
+ 'Uplay PC' => 35614,
+ 'Viber' => 32505,
+ 'Voo' => 32853,
+ 'VTM' => 38394,
+ 'Waze' => 36657,
+ 'WeTransfer' => 32523,
+ 'Whatsapp' => 32333,
+ 'Wikipedia' => 32425,
+ 'Wordfeud' => 22358,
+ 'Xbox Live' => 32481,
+ 'Yahoo Mail' => 34840,
+ 'Yellowbrick' => 37609,
+ 'Yeloplay' => 37359,
+ 'YouTube' => 32338,
+ 'Z1 Battle Royale' => 37258,
+ ),
+ 'Australia' => array(
+ '2k' => 36402,
+ '4chan' => 38290,
+ 'AAPT telecommunications' => 35849,
+ 'ABC' => 37712,
+ 'Activ8me' => 36814,
+ 'Adam Internet' => 33877,
+ 'Adelaide Bank' => 36729,
+ 'Adobe Creative Cloud' => 34553,
+ 'Airbnb' => 36403,
+ 'Alexa' => 36922,
+ 'Amaysim' => 35654,
+ 'Amazon' => 36404,
+ 'Amazon Prime Video' => 36968,
+ 'Amazon Web Services' => 34093,
+ 'American Express' => 38173,
+ 'Amino Apps' => 39045,
+ 'Amnet' => 33878,
+ 'Anthem' => 38176,
+ 'ANZ' => 33364,
+ 'Apex Legends' => 38125,
+ 'App Store' => 35577,
+ 'Apple Music' => 35243,
+ 'Apple Store' => 34455,
+ 'ARK: Survival Evolved' => 38746,
+ 'Assassin\'s Creed' => 35008,
+ 'AusBBS' => 36812,
+ 'Aussie Broadband' => 37219,
+ 'Australia Post' => 37052,
+ 'Bank Australia' => 38682,
+ 'Bank of Melbourne' => 35356,
+ 'Bank of Queensland' => 37458,
+ 'Bank SA' => 35354,
+ 'Bankwest' => 34972,
+ 'Battlefield' => 37468,
+ 'Belong' => 37179,
+ 'Bendigo Bank' => 37715,
+ 'BigPond' => 33993,
+ 'Binance' => 36878,
+ 'Bing' => 32874,
+ 'Blizzard Battle.net' => 35053,
+ 'Blogger' => 32875,
+ 'Boom Beach' => 36871,
+ 'Box' => 32876,
+ 'Brawl Stars' => 38816,
+ 'Bumble' => 36809,
+ 'Call of Duty' => 36405,
+ 'Candy Crush' => 35092,
+ 'Centrelink' => 37549,
+ 'Centurylink' => 34131,
+ 'Citibank' => 36507,
+ 'Clash of Clans' => 37302,
+ 'Clash Royale' => 38953,
+ 'Cloudflare' => 32877,
+ 'ClubTelco' => 34792,
+ 'Coinbase' => 36802,
+ 'Coinspot' => 36927,
+ 'Commander' => 37714,
+ 'Commonwealth Bank' => 33362,
+ 'Counter-strike' => 35059,
+ 'Crackle' => 35112,
+ 'Craigslist' => 32878,
+ 'Crunchyroll' => 36717,
+ 'Dead By Daylight' => 37415,
+ 'Deezer' => 33833,
+ 'Deliveroo' => 38197,
+ 'Destiny' => 34894,
+ 'DFP' => 35002,
+ 'Discord' => 36022,
+ 'Dodo' => 34003,
+ 'Doordash' => 39006,
+ 'Dota 2' => 35405,
+ 'Dropbox' => 32879,
+ 'EA' => 34509,
+ 'eBay' => 32880,
+ 'Eftel' => 35553,
+ 'Elite: Dangerous' => 37104,
+ 'Escape from Tarkov' => 38626,
+ 'ESPN' => 38387,
+ 'Etsy' => 37481,
+ 'Exchange Online' => 34545,
+ 'Exetel' => 34478,
+ 'Facebook' => 32881,
+ 'Facebook Messenger' => 32882,
+ 'Facetime' => 34601,
+ 'Fallout' => 35432,
+ 'Far Cry' => 37190,
+ 'Fifa' => 35473,
+ 'Fitbit' => 38358,
+ 'Flickr' => 32883,
+ 'Fonality' => 34313,
+ 'For Honor' => 35989,
+ 'Fortnite' => 36622,
+ 'Foxtel' => 33355,
+ 'Funimation' => 38583,
+ 'Game of war' => 35416,
+ 'Gears of War' => 38894,
+ 'Ghost Recon' => 36008,
+ 'GitHub' => 36529,
+ 'Gmail' => 32885,
+ 'Go Daddy' => 36619,
+ 'Google' => 32886,
+ 'Google Drive' => 34274,
+ 'Google Hangouts' => 32887,
+ 'Google Home' => 37343,
+ 'Google Play' => 32888,
+ 'Gran Turismo' => 36875,
+ 'Grindr' => 35834,
+ 'GTA 5' => 34755,
+ 'Guild Wars 2' => 36408,
+ 'Gumtree' => 33360,
+ 'Halo' => 35449,
+ 'Hay Day' => 34786,
+ 'Hayu' => 38366,
+ 'Hearthstone' => 38660,
+ 'Heronet' => 35949,
+ 'Hipchat' => 34867,
+ 'Hootsuite' => 32889,
+ 'iCloud' => 32890,
+ 'iiNet' => 33555,
+ 'iMessage' => 32891,
+ 'Imgur' => 32892,
+ 'Instagram' => 32893,
+ 'Internode' => 34477,
+ 'iPrimus' => 33876,
+ 'iTunes' => 32894,
+ 'Kik' => 32895,
+ 'Kraken' => 36849,
+ 'Ladbrokes' => 37640,
+ 'LastPass' => 34776,
+ 'League of Legends' => 35049,
+ 'LinkedIn' => 32896,
+ 'Mail.com' => 34799,
+ 'Mailbox' => 34834,
+ 'Mate Communicate' => 36813,
+ 'McDonalds app' => 37525,
+ 'ME Bank' => 34973,
+ 'Microsoft Azure' => 32917,
+ 'Microsoft Teams' => 38694,
+ 'Minecraft' => 32897,
+ 'My Fitness Pal' => 37633,
+ 'My Republic' => 35982,
+ 'MyGov' => 37550,
+ 'MyNetFone' => 35481,
+ 'myob' => 36343,
+ 'NAB' => 33365,
+ 'National Broadband Network, NBN' => 35992,
+ 'NBA 2k' => 37736,
+ 'Netflix' => 35177,
+ 'Netregistry' => 36060,
+ 'Netspeed' => 34492,
+ 'Nine' => 37000,
+ 'Nintendo eShop' => 34102,
+ 'Nintendo Network' => 35517,
+ 'Nintendo Switch Online' => 37243,
+ 'No Man\'s Sky' => 37404,
+ 'Office 365' => 34543,
+ 'OkCupid' => 38489,
+ 'OneDrive' => 32904,
+ 'Optus' => 33356,
+ 'Origin' => 35091,
+ 'Outlook' => 32899,
+ 'Overwatch' => 35683,
+ 'Paladins' => 37656,
+ 'Pandora' => 33343,
+ 'Panthur' => 36346,
+ 'Path of Exile' => 36498,
+ 'Paypal' => 35607,
+ 'Photobucket' => 32901,
+ 'Pinterest' => 32902,
+ 'Player Unknown\'s Battlegrounds' => 36356,
+ 'Playstation Network' => 34842,
+ 'PlentyOfFish' => 37416,
+ 'Pokémon Go' => 35732,
+ 'Project Online' => 34542,
+ 'Quickbooks Online' => 38220,
+ 'Rabobank' => 34974,
+ 'Rabodirect' => 34975,
+ 'Rainbow Six' => 35478,
+ 'Red Dead Redemption' => 37740,
+ 'Reddit' => 34843,
+ 'Roblox' => 36832,
+ 'Rocket League' => 35497,
+ 'Runescape' => 35106,
+ 'Salesforce' => 32903,
+ 'Sarahah' => 36374,
+ 'SBS' => 34703,
+ 'Sea of Thieves' => 37115,
+ 'Sharepoint Online' => 34541,
+ 'Skype' => 32905,
+ 'Skype for Business' => 34544,
+ 'Slack' => 35937,
+ 'Slideshare' => 32906,
+ 'Smite' => 35406,
+ 'Snapchat' => 32907,
+ 'Soundcloud' => 37230,
+ 'Spintel' => 35962,
+ 'Sportsbet' => 37713,
+ 'Spotify' => 33225,
+ 'St. George Bank' => 35353,
+ 'Stan' => 35503,
+ 'Star Wars Battlefront' => 35552,
+ 'Steam' => 34114,
+ 'Steep' => 37922,
+ 'Summoners War' => 37418,
+ 'Suncorp Bank' => 34432,
+ 'Sure Telecom' => 34394,
+ 'Tango' => 33742,
+ 'Teamviewer' => 34617,
+ 'Telegram' => 34220,
+ 'Telstra' => 33354,
+ 'The Division' => 35572,
+ 'The elder scrolls online' => 36554,
+ 'The Simpsons Tapped out' => 38166,
+ 'Think Mobile' => 34527,
+ 'Tiktok' => 39061,
+ 'Tinder' => 34241,
+ 'TPG Telecom' => 33359,
+ 'Tumblr' => 32910,
+ 'TuneIn' => 38761,
+ 'Tweakbox' => 38346,
+ 'Twitch' => 35026,
+ 'Twitter' => 32911,
+ 'Uber' => 37766,
+ 'Uber Eats' => 38272,
+ 'Uberglobal' => 35669,
+ 'Udemy' => 37719,
+ 'Uplay PC' => 36211,
+ 'V4 Telecom' => 37357,
+ 'Vaya' => 34518,
+ 'Viber' => 32912,
+ 'Vimeo' => 32913,
+ 'Virgin Mobile' => 34516,
+ 'Vocus' => 37711,
+ 'Vodafone' => 33357,
+ 'War Thunder' => 38361,
+ 'Warframe' => 36495,
+ 'Wattpad' => 34694,
+ 'Waze' => 33405,
+ 'Webex' => 34162,
+ 'Weebly' => 34911,
+ 'Westnet' => 35163,
+ 'Westpac' => 33363,
+ 'WeTransfer' => 32914,
+ 'Whatsapp' => 32915,
+ 'Wikipedia' => 32916,
+ 'Wish' => 39042,
+ 'Wix' => 37255,
+ 'Wordpress.com' => 32918,
+ 'World of Tanks' => 37191,
+ 'World of Warcraft' => 35054,
+ 'WWE Network' => 38722,
+ 'Xbox Live' => 34283,
+ 'Xero' => 36177,
+ 'Yahoo' => 32919,
+ 'Yahoo Mail' => 32920,
+ 'Yahoo Messenger' => 32921,
+ 'Yelp' => 32922,
+ 'Youtube' => 32923,
+ 'Youtube Music' => 37590,
+ 'Z1 Battle Royale' => 35494,
+ 'Zettanet' => 35655,
+ 'ZoHo' => 37551,
+ ),
+ 'Canada' => array(
+ '2k' => 36723,
+ 'Acanac' => 34107,
+ 'Access' => 33069,
+ 'Aeroplan' => 35789,
+ 'Air Canada' => 37029,
+ 'Air Miles' => 35788,
+ 'Airbnb' => 37423,
+ 'Alaska Airlines' => 32926,
+ 'Alexa' => 37067,
+ 'Allegiant Air' => 32927,
+ 'Allstream' => 34001,
+ 'Altima Telecom' => 37247,
+ 'Amazon' => 32928,
+ 'Amazon Prime Music' => 38907,
+ 'Amazon Prime Video' => 37393,
+ 'Amazon Web Services' => 32929,
+ 'American Airlines' => 32930,
+ 'American Express' => 38172,
+ 'Amino Apps' => 38716,
+ 'Anthem' => 38056,
+ 'Anydesk' => 37488,
+ 'Apex Legends' => 38113,
+ 'App Store' => 35576,
+ 'Apple Music' => 35244,
+ 'Apple Store' => 34456,
+ 'ARK: Survival Evolved' => 38747,
+ 'Assassin\'s Creed' => 35007,
+ 'BabyTEL' => 35360,
+ 'Battlefield' => 36923,
+ 'BC Hydro' => 35806,
+ 'Beanfield' => 36663,
+ 'beIN' => 38788,
+ 'Bell' => 32936,
+ 'Bell Aliant' => 32937,
+ 'Bet365' => 39064,
+ 'Binance' => 36876,
+ 'Bing' => 32938,
+ 'Black Desert Online' => 38829,
+ 'Blizzard Battle.net' => 34488,
+ 'Blogger' => 32940,
+ 'BMO' => 34525,
+ 'Boom Beach' => 36558,
+ 'Box' => 32941,
+ 'Brama Telecom' => 34146,
+ 'Brawl Stars' => 38833,
+ 'Bumble' => 36330,
+ 'Call of Duty' => 34149,
+ 'Candy Crush' => 35093,
+ 'Capital One' => 36410,
+ 'Carry Telecom' => 37695,
+ 'CBC' => 34267,
+ 'Centurylink' => 35627,
+ 'Chatr' => 34005,
+ 'CIBC' => 34526,
+ 'CIK Telecom‎' => 34428,
+ 'Clash of Clans' => 34445,
+ 'Clash Royale' => 37523,
+ 'Cloudflare' => 32952,
+ 'CNN' => 37372,
+ 'Cogeco' => 32953,
+ 'Cogent' => 35556,
+ 'Coinbase' => 36800,
+ 'Colbanet' => 37542,
+ 'CommStream' => 36028,
+ 'Comwave' => 36641,
+ 'Counter-strike' => 35056,
+ 'Crackle' => 35111,
+ 'Craigslist' => 32956,
+ 'Crave TV' => 35621,
+ 'Crunchyroll' => 36716,
+ 'Dark Souls' => 36557,
+ 'DayZ' => 39007,
+ 'Dazn' => 36510,
+ 'Dead By Daylight' => 36595,
+ 'Delta Air Lines' => 32958,
+ 'Destiny' => 34892,
+ 'DFP' => 35001,
+ 'Diablo' => 39071,
+ 'Discord' => 36411,
+ 'Distributel' => 33870,
+ 'Doordash' => 38385,
+ 'Dota 2' => 35404,
+ 'Dropbox' => 32961,
+ 'EA' => 34504,
+ 'EA Sports UFC' => 36552,
+ 'Eastlink' => 33414,
+ 'eBay' => 32964,
+ 'Ebox' => 35555,
+ 'Ecobee' => 38021,
+ 'Elite: Dangerous' => 37103,
+ 'Epic Games Store' => 38767,
+ 'Equitable Bank' => 36731,
+ 'Escape from Tarkov' => 37975,
+ 'Etsy' => 38265,
+ 'Exchange Online' => 34546,
+ 'Execulink' => 34942,
+ 'Expedia' => 37401,
+ 'Facebook' => 32965,
+ 'Facebook Messenger' => 32966,
+ 'Facetime' => 34595,
+ 'Fallout' => 37663,
+ 'FedEx' => 36500,
+ 'Fido' => 34000,
+ 'Fifa' => 35472,
+ 'Fitbit' => 38359,
+ 'Flickr' => 32967,
+ 'For Honor' => 35986,
+ 'Fortnite' => 36623,
+ 'Forza' => 38836,
+ 'Fox News' => 37665,
+ 'Freedom Mobile' => 33869,
+ 'Friday the 13th The Game' => 37562,
+ 'Funimation' => 37744,
+ 'Game of war' => 35415,
+ 'Garmin Connect' => 38540,
+ 'Gears of War' => 35938,
+ 'Ghost Recon' => 37772,
+ 'GitHub' => 32970,
+ 'Gmail' => 32971,
+ 'Go Daddy' => 34943,
+ 'GO Transit' => 32972,
+ 'Google' => 32973,
+ 'Google Calendar' => 38599,
+ 'Google Cloud' => 38537,
+ 'Google Drive' => 34272,
+ 'Google Hangouts' => 32974,
+ 'Google Home' => 36141,
+ 'Google Play' => 32975,
+ 'GoToMeeting' => 36504,
+ 'Gran Turismo' => 36679,
+ 'Grindr' => 35835,
+ 'GTA 5' => 34756,
+ 'Guild Wars 2' => 36406,
+ 'Halo' => 35450,
+ 'Harry Potter: Wizards Unite' => 38687,
+ 'Hay Day' => 34789,
+ 'Hayu' => 38789,
+ 'Hearthstone' => 38289,
+ 'Hipchat' => 34868,
+ 'Hootsuite' => 32977,
+ 'HQ Trivia' => 37027,
+ 'HSBC' => 39048,
+ 'Hue' => 37814,
+ 'HughesNet' => 32978,
+ 'iCloud' => 32979,
+ 'iMessage' => 33249,
+ 'Imgur' => 32981,
+ 'IMVU' => 37472,
+ 'Indeed' => 38782,
+ 'Instagram' => 32982,
+ 'Interac' => 39049,
+ 'iTunes' => 32983,
+ 'JetBlue Airways' => 32984,
+ 'Jira' => 38545,
+ 'Juno' => 32985,
+ 'Kijiji' => 34303,
+ 'Kik' => 32986,
+ 'Koodo' => 34002,
+ 'Kraken' => 36750,
+ 'LastPass' => 36785,
+ 'League of Legends' => 35047,
+ 'Lightspeed' => 37066,
+ 'LinkedIn' => 32987,
+ 'Madden' => 38459,
+ 'Mail.com' => 34801,
+ 'Mailbox' => 34837,
+ 'McDonalds app' => 37642,
+ 'MCSNet' => 35889,
+ 'Metro Loop' => 37646,
+ 'Microsoft Azure' => 33057,
+ 'Minecraft' => 32996,
+ 'Mixer' => 38769,
+ 'MLB The Show' => 36989,
+ 'MLB TV' => 37189,
+ 'Montréal Metro' => 32997,
+ 'Mordhau' => 38734,
+ 'MTS' => 33868,
+ 'My Fitness Pal' => 37632,
+ 'NBA 2k' => 37722,
+ 'Nest' => 35191,
+ 'Netflix' => 32998,
+ 'NetZero' => 32999,
+ 'Neverwinter' => 35766,
+ 'Nintendo eShop' => 34101,
+ 'Nintendo Network' => 35518,
+ 'No Man\'s Sky' => 38779,
+ 'NorthernTel' => 34636,
+ 'Northwestel' => 35104,
+ 'Office 365' => 34548,
+ 'OkCupid' => 36678,
+ 'OneDrive' => 33020,
+ 'Oricom Internet' => 35829,
+ 'Origin' => 36584,
+ 'Outlook' => 33005,
+ 'Overwatch' => 35682,
+ 'Paladins' => 37664,
+ 'Path of Exile' => 36481,
+ 'Paypal' => 33010,
+ 'PC Optimum' => 37216,
+ 'Peer 1' => 34824,
+ 'Photobucket' => 33011,
+ 'Pinterest' => 33012,
+ 'Piper' => 38323,
+ 'Player Unknown\'s Battlegrounds' => 36337,
+ 'Playstation Network' => 33013,
+ 'PlentyOfFish' => 35798,
+ 'Pokémon Go' => 35734,
+ 'Pokerstars' => 38174,
+ 'Primus' => 33872,
+ 'Qtrade Financial Group' => 36025,
+ 'Quickbooks Online' => 37607,
+ 'Quizup' => 34297,
+ 'Rabb.it' => 37974,
+ 'Rainbow Six' => 35477,
+ 'RBC' => 34521,
+ 'Red Dead Redemption' => 37742,
+ 'Reddit' => 34845,
+ 'Roblox' => 35785,
+ 'Rocket League' => 35498,
+ 'Rogers' => 33015,
+ 'Runescape' => 35105,
+ 'Salesforce' => 33016,
+ 'Sarahah' => 36514,
+ 'Sasktel' => 33871,
+ 'Scotiabank' => 34523,
+ 'Sea of Thieves' => 37111,
+ 'Sharepoint Online' => 34550,
+ 'Shaw' => 33551,
+ 'Shopify' => 35863,
+ 'Signal' => 36328,
+ 'Simplii' => 37541,
+ 'SiriusXM' => 38561,
+ 'SkipTheDishes' => 38322,
+ 'Skype' => 33021,
+ 'Skype for Business' => 34547,
+ 'Slack' => 35935,
+ 'Slideshare' => 33023,
+ 'Smartsheet' => 38724,
+ 'Smite' => 37026,
+ 'Snapchat' => 33024,
+ 'Soundcloud' => 37229,
+ 'Sourceforge' => 33025,
+ 'Spotify' => 33028,
+ 'Star Wars Battlefront' => 35550,
+ 'Start Communications' => 34426,
+ 'Steam' => 33030,
+ 'Steep' => 37923,
+ 'Strava' => 38745,
+ 'Summoners War' => 37422,
+ 'Tangerine' => 37694,
+ 'Tango' => 33741,
+ 'Tbaytel' => 34612,
+ 'TD Canada Trust' => 34522,
+ 'Teamviewer' => 34618,
+ 'TekSavvy' => 33867,
+ 'Télébec' => 34110,
+ 'Telegram' => 34228,
+ 'Telnet' => 34158,
+ 'Telus' => 33034,
+ 'TeraGo' => 34427,
+ 'Tesla' => 38835,
+ 'The Division' => 35571,
+ 'The elder scrolls online' => 36399,
+ 'The Simpsons Tapped out' => 35109,
+ 'The Weather Channel' => 38837,
+ 'Ticketmaster' => 39008,
+ 'Tiktok' => 38727,
+ 'Tinder' => 34239,
+ 'Toronto Transit Commission' => 33036,
+ 'Translink' => 33039,
+ 'Trello' => 39066,
+ 'Trove' => 38825,
+ 'Tumblr' => 33040,
+ 'TuneIn' => 36037,
+ 'TurboTax' => 38213,
+ 'Tweakbox' => 38343,
+ 'Twitch' => 35023,
+ 'Twitter' => 33042,
+ 'Uber' => 37765,
+ 'Uber Eats' => 38022,
+ 'Udemy' => 37718,
+ 'United Airlines' => 33044,
+ 'Uplay PC' => 34688,
+ 'UPS' => 36831,
+ 'Vancity' => 37570,
+ 'Velcom' => 36978,
+ 'Viber' => 33348,
+ 'Vidéotron' => 33050,
+ 'Vimeo' => 33051,
+ 'Virgin Mobile' => 34096,
+ 'Visa' => 38693,
+ 'VMedia' => 34265,
+ 'Warface' => 38777,
+ 'Warframe' => 36370,
+ 'Wattpad' => 34695,
+ 'Waveapps' => 35960,
+ 'Waze' => 33406,
+ 'Webex' => 34160,
+ 'Weight Watchers' => 35664,
+ 'WestJet' => 35648,
+ 'WeTransfer' => 33054,
+ 'Whatsapp' => 33055,
+ 'Whisper' => 34625,
+ 'Wiband' => 34771,
+ 'Wikipedia' => 33056,
+ 'Wish' => 39041,
+ 'Wisp' => 37218,
+ 'Wordpress.com' => 33059,
+ 'World of Tanks' => 35527,
+ 'World of Warcraft' => 34264,
+ 'WWE Network' => 38717,
+ 'Xbox Live' => 33061,
+ 'Xplornet' => 34270,
+ 'Yahoo' => 33063,
+ 'Yahoo Mail' => 33064,
+ 'Yahoo Messenger' => 33065,
+ 'Yak' => 34269,
+ 'Yelp' => 33066,
+ 'Youtube' => 33067,
+ 'Youtube Music' => 37588,
+ 'Yubo' => 38961,
+ 'Z1 Battle Royale' => 35491,
+ 'ZoHo' => 36038,
+ 'Zoom' => 37947,
+ 'Zynga' => 33068,
+ ),
+ 'Hong Kong' => array(
+ '3 (Three)' => 36202,
+ 'Apex Legends' => 38178,
+ 'App Store' => 37734,
+ 'Binance' => 37023,
+ 'Blizzard Battle.net' => 36186,
+ 'China Mobile' => 36199,
+ 'Cloudflare' => 38641,
+ 'Counter-strike' => 38725,
+ 'CSL' => 36200,
+ 'Discord' => 38608,
+ 'EA' => 36700,
+ 'eBay' => 36207,
+ 'Facebook' => 36185,
+ 'Fifa' => 37604,
+ 'For Honor' => 36187,
+ 'Ghost Recon' => 38990,
+ 'Gmail' => 36188,
+ 'Google' => 36210,
+ 'Google Drive' => 38264,
+ 'Google Play' => 38526,
+ 'GTA 5' => 37279,
+ 'Hong Kong Broadband Network' => 36204,
+ 'iCloud' => 38842,
+ 'Instagram' => 36392,
+ 'Kraken' => 36984,
+ 'Netflix' => 36213,
+ 'Netvigator' => 36203,
+ 'Office 365' => 37172,
+ 'Origin' => 38396,
+ 'Outlook' => 36189,
+ 'Overwatch' => 36190,
+ 'PCCW' => 36205,
+ 'Player Unknown\'s Battlegrounds' => 36617,
+ 'Playstation Network' => 36191,
+ 'Pokémon Go' => 36192,
+ 'Rainbow Six' => 36193,
+ 'Reddit' => 37479,
+ 'Skype' => 36194,
+ 'Smartone' => 36198,
+ 'Snapchat' => 36208,
+ 'Steam' => 38650,
+ 'Telegram' => 36195,
+ 'Three Home Broadband' => 36206,
+ 'Tinder' => 36196,
+ 'TuneIn' => 36036,
+ 'Twitter' => 38671,
+ 'Uplay PC' => 36212,
+ 'Whatsapp' => 36197,
+ 'Yahoo Mail' => 36769,
+ 'Youtube' => 36209,
+ ),
+ 'Ireland' => array(
+ '3 (Three)' => 34214,
+ 'AIB (Allied Irish Banks)' => 34209,
+ 'Amazon' => 34165,
+ 'Apex Legends' => 38133,
+ 'App Store' => 38557,
+ 'Apple Store' => 34460,
+ 'Bank of Ireland' => 37754,
+ 'Battlefield' => 38451,
+ 'Binance' => 36931,
+ 'Bing' => 34166,
+ 'Boom Beach' => 35153,
+ 'Call of Duty' => 36709,
+ 'Counter-strike' => 38233,
+ 'Craigslist' => 34167,
+ 'Crunchyroll' => 38094,
+ 'Dead By Daylight' => 37444,
+ 'Deezer' => 34168,
+ 'Destiny' => 38615,
+ 'Digiweb' => 34875,
+ 'Discord' => 37390,
+ 'DoneDeal' => 34208,
+ 'EA' => 36413,
+ 'eBay' => 34169,
+ 'Eir' => 34210,
+ 'eMobile' => 34211,
+ 'Facebook' => 34170,
+ 'Facebook Messenger' => 34171,
+ 'Facetime' => 34584,
+ 'Fifa' => 36907,
+ 'Fortnite' => 36692,
+ 'Ghost Recon' => 38992,
+ 'Gmail' => 34172,
+ 'Google' => 34173,
+ 'Google Hangouts' => 34174,
+ 'Google Play' => 34175,
+ 'Gran Turismo' => 36949,
+ 'Grindr' => 36755,
+ 'GTA 5' => 37275,
+ 'Hootsuite' => 34176,
+ 'iCloud' => 34177,
+ 'Imagine' => 34425,
+ 'iMessage' => 34178,
+ 'Imgur' => 34179,
+ 'Instagram' => 34180,
+ 'iTunes' => 34181,
+ 'Kik' => 34182,
+ 'Kraken' => 36850,
+ 'Ladbrokes' => 37469,
+ 'LinkedIn' => 34183,
+ 'Magnet' => 34424,
+ 'Meteor' => 34213,
+ 'My Fitness Pal' => 37634,
+ 'Nest' => 35193,
+ 'Netflix' => 34184,
+ 'Now TV' => 38403,
+ 'O2' => 34206,
+ 'Office 365' => 35441,
+ 'Origin' => 36890,
+ 'Outlook' => 34185,
+ 'Overwatch' => 36484,
+ 'Paddy Power' => 38360,
+ 'Pinterest' => 34186,
+ 'Playstation Network' => 34187,
+ 'PlentyOfFish' => 37417,
+ 'Pokémon Go' => 35758,
+ 'Rabodirect' => 34979,
+ 'Rainbow Six' => 36414,
+ 'Red Dead Redemption' => 38288,
+ 'Reddit' => 36826,
+ 'Roblox' => 38756,
+ 'Rocket League' => 36670,
+ 'Ryanair' => 37253,
+ 'Sky' => 34212,
+ 'Skype' => 37018,
+ 'Sleepless' => 38314,
+ 'Snapchat' => 34188,
+ 'Spotify' => 34189,
+ 'Steam' => 34190,
+ 'Strava' => 38643,
+ 'Teamviewer' => 37631,
+ 'Telegram' => 37226,
+ 'Tinder' => 34864,
+ 'Tumblr' => 34191,
+ 'TuneIn' => 38760,
+ 'Twitch' => 36538,
+ 'Twitter' => 34192,
+ 'Ulster Bank' => 36070,
+ 'Viber' => 34193,
+ 'Vimeo' => 34194,
+ 'Virgin Media' => 34207,
+ 'Vodafone' => 34196,
+ 'Wattpad' => 34699,
+ 'Waze' => 34197,
+ 'Webex' => 34198,
+ 'Whatsapp' => 34199,
+ 'Wikipedia' => 34200,
+ 'Xbox Live' => 34201,
+ 'Yahoo' => 34202,
+ 'Yahoo Mail' => 34203,
+ 'Yahoo Messenger' => 34204,
+ 'Youtube' => 34205,
+ 'Youtube Music' => 37589,
+ 'Z1 Battle Royale' => 37261,
+ ),
+ 'Danmark' => array(
+ '3 (Tre)' => 33694,
+ 'Amazon' => 33651,
+ 'Anthem' => 38212,
+ 'Apex Legends' => 38128,
+ 'App Store' => 38554,
+ 'Apple Store' => 34452,
+ 'Battlefield' => 37097,
+ 'Bet365' => 38813,
+ 'Bibob' => 33841,
+ 'Binance' => 36930,
+ 'Blizzard Battle.net' => 36162,
+ 'Call of Duty' => 36707,
+ 'CBB Mobil' => 33840,
+ 'Counter-strike' => 36171,
+ 'Crunchyroll' => 36721,
+ 'Danske Bank' => 33687,
+ 'DBA' => 33700,
+ 'Dead By Daylight' => 37427,
+ 'Deezer' => 33835,
+ 'Destiny' => 36593,
+ 'Discord' => 36682,
+ 'DMI' => 36121,
+ 'Dota 2' => 36398,
+ 'EA' => 35496,
+ 'eBay' => 34862,
+ 'EnergiMidt' => 34435,
+ 'Epic Games Store' => 39025,
+ 'Ewii' => 34436,
+ 'Facebook' => 33652,
+ 'Facebook Messenger' => 33653,
+ 'Faceit' => 38542,
+ 'Facetime' => 34590,
+ 'Fifa' => 36621,
+ 'For Honor' => 36163,
+ 'Fortnite' => 36690,
+ 'Fullrate' => 34433,
+ 'Ghost Recon' => 39002,
+ 'Gmail' => 33654,
+ 'Google' => 33655,
+ 'Google Drive' => 36606,
+ 'Google Hangouts' => 33656,
+ 'Google Play' => 33657,
+ 'Gran Turismo' => 36915,
+ 'GTA 5' => 36170,
+ 'Guild Wars 2' => 36469,
+ 'HBO Nordic' => 35605,
+ 'iCloud' => 33658,
+ 'iMessage' => 33659,
+ 'Instagram' => 33660,
+ 'iTunes' => 33661,
+ 'Kik' => 33705,
+ 'Kraken' => 36851,
+ 'Kviknet' => 38016,
+ 'League of Legends' => 36166,
+ 'LinkedIn' => 33701,
+ 'Minecraft' => 37282,
+ 'Net 1' => 33725,
+ 'Netflix' => 33689,
+ 'Nordea' => 33688,
+ 'Office 365' => 35440,
+ 'OneDrive' => 36867,
+ 'Origin' => 36894,
+ 'Outlook' => 33662,
+ 'Overwatch' => 36165,
+ 'Path of Exile' => 36482,
+ 'Playerunknown\'s Battlegrounds' => 36334,
+ 'Playstation Network' => 33663,
+ 'Pokémon Go' => 35753,
+ 'Rainbow Six' => 36161,
+ 'Realm Royale' => 37306,
+ 'Red Dead Redemption' => 38306,
+ 'Reddit' => 36824,
+ 'Roblox' => 36612,
+ 'Rocket League' => 35977,
+ 'Sea of Thieves' => 37122,
+ 'Skype' => 33686,
+ 'Snapchat' => 33696,
+ 'Spotify' => 33697,
+ 'Steam' => 34277,
+ 'Stofa' => 34434,
+ 'TDC' => 33691,
+ 'Teamviewer' => 35693,
+ 'Telegram' => 37181,
+ 'Telenor' => 33692,
+ 'Telia' => 33693,
+ 'Tinder' => 34861,
+ 'Twitch' => 35508,
+ 'Twitter' => 33664,
+ 'Uplay PC' => 35610,
+ 'Viaplay' => 37292,
+ 'Viber' => 33698,
+ 'Warframe' => 36703,
+ 'Whatsapp' => 33703,
+ 'Wikipedia' => 33665,
+ 'Wordfeud' => 33702,
+ 'World of Warcraft' => 36168,
+ 'World of Warships' => 38013,
+ 'Xbox Live' => 33666,
+ 'Yahoo Mail' => 37043,
+ 'Youmusic' => 33699,
+ 'Yousee' => 33695,
+ 'Youtube' => 33667,
+ 'Z1 Battle Royale' => 37265,
+ ),
+ 'Sverige' => array(
+ '3 (Tre)' => 33722,
+ 'A3' => 38249,
+ 'Amazon' => 33668,
+ 'Anthem' => 38190,
+ 'Apex Legends' => 38115,
+ 'App Store' => 38101,
+ 'Apple Store' => 34450,
+ 'Bahnhof' => 34417,
+ 'BankID' => 33845,
+ 'Battlefield' => 37093,
+ 'Bet365' => 38812,
+ 'Binance' => 36933,
+ 'Blizzard Battle.net' => 34484,
+ 'Blocket' => 33716,
+ 'Boxer' => 37572,
+ 'Bredband2' => 34418,
+ 'Bredbandsbolaget' => 33843,
+ 'Bredbandsson' => 36049,
+ 'Call of Duty' => 35539,
+ 'Com Hem' => 34416,
+ 'Counter-strike' => 36172,
+ 'Crunchyroll' => 36719,
+ 'Dead By Daylight' => 36598,
+ 'Destiny' => 35510,
+ 'Discord' => 36764,
+ 'Dota 2' => 35876,
+ 'EA' => 35509,
+ 'eBay' => 34863,
+ 'Epic Games Store' => 39023,
+ 'Escape from Tarkov' => 38107,
+ 'Eurosport Player' => 36613,
+ 'Facebook' => 33669,
+ 'Facebook Messenger' => 33670,
+ 'Faceit' => 39039,
+ 'Facetime' => 34589,
+ 'Fifa' => 36909,
+ 'For Honor' => 35998,
+ 'Fortnite' => 36685,
+ 'Ghost Recon' => 39003,
+ 'Glocalnet' => 33842,
+ 'Gmail' => 33671,
+ 'Google' => 33672,
+ 'Google Drive' => 36604,
+ 'Google Hangouts' => 33673,
+ 'Google Play' => 33674,
+ 'Gran Turismo' => 36914,
+ 'Grindr' => 38739,
+ 'GTA 5' => 35528,
+ 'Guild Wars 2' => 36466,
+ 'Halebop' => 33726,
+ 'Handelsbanken' => 33718,
+ 'Hay Day' => 38214,
+ 'HBO Nordic' => 35606,
+ 'Hearthstone' => 38659,
+ 'Hue' => 37816,
+ 'iCloud' => 33675,
+ 'Ikano Bank' => 36578,
+ 'iMessage' => 33676,
+ 'Instagram' => 33677,
+ 'iTunes' => 33678,
+ 'Kik' => 33704,
+ 'Kraken' => 36829,
+ 'League of Legends' => 36167,
+ 'LinkedIn' => 33714,
+ 'Minecraft' => 37281,
+ 'Net 1' => 33724,
+ 'Netflix' => 33706,
+ 'Nordea' => 33717,
+ 'Office 365' => 35439,
+ 'OneDrive' => 36869,
+ 'Origin' => 36898,
+ 'Outlook' => 33679,
+ 'Overwatch' => 36150,
+ 'Path of Exile' => 36480,
+ 'Playerunknown\'s Battlegrounds' => 36333,
+ 'Playstation Network' => 33707,
+ 'Pokémon Go' => 35749,
+ 'Rainbow Six' => 36148,
+ 'Realm Royale' => 37307,
+ 'Red Dead Redemption' => 38285,
+ 'Reddit' => 35883,
+ 'Riksnet' => 37486,
+ 'Roblox' => 36611,
+ 'Rocket League' => 35487,
+ 'Sea of Thieves' => 37114,
+ 'SEB' => 33719,
+ 'SF Anytime' => 37573,
+ 'SkandiaBanken' => 34021,
+ 'Skype' => 33708,
+ 'Slack' => 37495,
+ 'Snapchat' => 33709,
+ 'Soundcloud' => 37228,
+ 'Sparbanken Öresund' => 34310,
+ 'Spotify' => 33838,
+ 'Steam' => 34135,
+ 'Swedbank' => 33713,
+ 'Swish' => 35777,
+ 'Teamviewer' => 35692,
+ 'Tele2' => 33721,
+ 'Telegram' => 35969,
+ 'Telenor' => 33723,
+ 'Telia' => 33720,
+ 'Telldus' => 36653,
+ 'The Elder Scrolls Online' => 36033,
+ 'Tinder' => 36458,
+ 'Tradera' => 33715,
+ 'Tumblr' => 36713,
+ 'Tweakbox' => 38905,
+ 'Twitch' => 35507,
+ 'Twitter' => 33710,
+ 'Uplay PC' => 35609,
+ 'Viaplay' => 37291,
+ 'Viber' => 37502,
+ 'Warframe' => 36701,
+ 'Whatsapp' => 33711,
+ 'Wikipedia' => 33682,
+ 'Wordfeud' => 33712,
+ 'World of Tanks' => 35488,
+ 'World of Warcraft' => 36169,
+ 'World of Warships' => 38011,
+ 'Xbox Live' => 33683,
+ 'Yahoo Mail' => 37044,
+ 'Youtube' => 33684,
+ 'Z1 Battle Royale' => 35493,
+ ),
+ 'Italia' => array(
+ '3 Italia' => 33154,
+ 'Airbnb' => 37345,
+ 'Aircomm' => 36015,
+ 'Alexa' => 38031,
+ 'AlternatYva' => 37556,
+ 'Amazon' => 33174,
+ 'Amazon Prime Video' => 36975,
+ 'Anthem' => 38189,
+ 'Anydesk' => 37491,
+ 'Apex Legends' => 38119,
+ 'App Store' => 37733,
+ 'Apple Store' => 34468,
+ 'Aruba' => 37217,
+ 'Banco di Napoli' => 33181,
+ 'Battlefield' => 37095,
+ 'Betclic' => 39047,
+ 'Binance' => 36937,
+ 'Blizzard Battle.net' => 37092,
+ 'BNL' => 33180,
+ 'Brawl Stars' => 38821,
+ 'Bwin' => 35072,
+ 'Call of Duty' => 35537,
+ 'Clash of Clans' => 34361,
+ 'Clash Royale' => 38956,
+ 'Cloudflare' => 38620,
+ 'Coinbase' => 36801,
+ 'Coopvoce' => 34921,
+ 'Counter-strike' => 36650,
+ 'Credito Emiliano - Credem' => 33182,
+ 'Crunchyroll' => 38095,
+ 'Dazn' => 37442,
+ 'Dead By Daylight' => 36627,
+ 'Deezer' => 33839,
+ 'Destiny' => 36590,
+ 'Discord' => 36767,
+ 'Dota 2' => 35878,
+ 'Dropbox' => 33175,
+ 'EA' => 34498,
+ 'EA Sports UFC' => 36553,
+ 'eBay' => 32816,
+ 'Elite: Dangerous' => 37774,
+ 'Eolo' => 37763,
+ 'Epic Games Store' => 39024,
+ 'Escape from Tarkov' => 39056,
+ 'Facebook' => 32812,
+ 'Facebook Messenger' => 32813,
+ 'Facetime' => 34598,
+ 'Fallout' => 37668,
+ 'Fastweb' => 33160,
+ 'Fifa' => 36910,
+ 'Fineco' => 33167,
+ 'Flickr' => 37949,
+ 'For Honor' => 35990,
+ 'Fortnite' => 36686,
+ 'Friday the 13th The Game' => 37564,
+ 'Ghost Recon' => 38999,
+ 'Gmail' => 32815,
+ 'Google' => 32805,
+ 'Google Drive' => 36607,
+ 'Google Hangouts' => 32806,
+ 'Google Play' => 32807,
+ 'Gran Turismo' => 36874,
+ 'Grindr' => 36757,
+ 'GTA5 ' => 35918,
+ 'Guild Wars 2' => 36472,
+ 'Ho' => 37408,
+ 'Hue' => 37813,
+ 'iCloud' => 33169,
+ 'Iliad' => 37214,
+ 'iMessage' => 33164,
+ 'Infinity' => 35972,
+ 'Infostrada' => 34711,
+ 'ING Direct' => 33168,
+ 'Instagram' => 33170,
+ 'Intesa Sanpaolo' => 33179,
+ 'iTunes' => 33159,
+ 'Kena Mobile' => 36364,
+ 'Kraken' => 36771,
+ 'League of Legends' => 37759,
+ 'Libero' => 33178,
+ 'LinkedIn' => 33177,
+ 'Linkem' => 34475,
+ 'Lottomatica' => 35068,
+ 'Lycamobile' => 38691,
+ 'Mc-link' => 34476,
+ 'Mediaset Premium' => 33162,
+ 'Mediaset TV Free' => 35973,
+ 'My Fitness Pal' => 37638,
+ 'Netflix' => 35568,
+ 'Neverwinter' => 36675,
+ 'NGI' => 34474,
+ 'Office 365' => 35443,
+ 'Onedrive' => 35411,
+ 'Origin' => 36897,
+ 'Outlook' => 33163,
+ 'Overwatch' => 36384,
+ 'Paddy Power' => 35069,
+ 'Paladins' => 36379,
+ 'Path of Exile' => 37726,
+ 'Paypal' => 33166,
+ 'Player Unknown\'s Battlegrounds' => 36567,
+ 'Playstation Network' => 32818,
+ 'Pokémon Go' => 35737,
+ 'Poste Italiane' => 37361,
+ 'PosteMobile' => 37360,
+ 'Quizduello' => 34299,
+ 'Rainbow Six' => 36045,
+ 'Red Dead Redemption' => 38284,
+ 'Reddit' => 37367,
+ 'Roblox' => 38916,
+ 'Rocket League' => 35979,
+ 'Ruzzle' => 33967,
+ 'Ryanair' => 37519,
+ 'Sea of Thieves' => 37121,
+ 'Sisal' => 35066,
+ 'Sky' => 33155,
+ 'Skype' => 32821,
+ 'Slack' => 37341,
+ 'SNAI' => 35067,
+ 'Snapchat' => 36446,
+ 'Spotify' => 33176,
+ 'Steam' => 34136,
+ 'Tango' => 33743,
+ 'Teamviewer' => 35455,
+ 'Telegram' => 34904,
+ 'The elder scrolls online' => 37327,
+ 'TIM' => 33158,
+ 'TimMusic' => 35913,
+ 'TimVision' => 35908,
+ 'Tinder' => 36549,
+ 'Tiscali' => 33161,
+ 'Tumblr' => 36712,
+ 'Tweakbox' => 38344,
+ 'Twitch' => 35604,
+ 'Twitter' => 32814,
+ 'UniCredit' => 33171,
+ 'Uplay PC' => 35613,
+ 'Viber' => 33403,
+ 'Virgilio' => 36459,
+ 'Vodafone' => 33156,
+ 'Warface' => 38765,
+ 'Warframe' => 36492,
+ 'WeBank' => 33173,
+ 'WeTransfer' => 36445,
+ 'Whatsapp' => 32820,
+ 'Wifi Trenitalia' => 35974,
+ 'Wikipedia' => 33172,
+ 'William Hill' => 35070,
+ 'Wind' => 33157,
+ 'World of Warships' => 38012,
+ 'Xbox Live' => 32819,
+ 'Yahoo' => 32809,
+ 'Yahoo Mail' => 32810,
+ 'Yahoo Messenger' => 32811,
+ 'Youtube' => 32808,
+ 'Z1 Battle Royale' => 37254,
+ 'ZoHo' => 37554,
+ ),
+ 'South Africa' => array(
+ 'ABSA' => 33599,
+ 'Afrihost' => 35660,
+ 'Amazon' => 33578,
+ 'Apex Legends' => 38157,
+ 'Apple Store' => 34458,
+ 'Axxess' => 35618,
+ 'Bidorbuy' => 33596,
+ 'Binance' => 36941,
+ 'Bing' => 33579,
+ 'Blizzard Battle.net' => 37661,
+ 'Call of Duty' => 34152,
+ 'Capitec' => 36966,
+ 'Cell C' => 33602,
+ 'Clash Royale' => 38946,
+ 'Cool Ideas' => 38326,
+ 'Counter-strike' => 36512,
+ 'Cybersmart' => 34619,
+ 'Dead By Daylight' => 37435,
+ 'Deezer' => 33834,
+ 'Destiny' => 38981,
+ 'DirecTV Now' => 35915,
+ 'Discord' => 38611,
+ 'Discovery' => 38334,
+ 'Dota 2' => 36428,
+ 'DSTv' => 33607,
+ 'EA' => 34507,
+ 'eBay' => 33581,
+ 'Eskom' => 38333,
+ 'Facebook' => 33582,
+ 'Facebook Messenger' => 37737,
+ 'Fifa' => 38436,
+ 'First National Bank (FNB)' => 33597,
+ 'Fortnite' => 36710,
+ 'Ghost Recon' => 38994,
+ 'Gmail' => 33583,
+ 'Google' => 33584,
+ 'Google Hangouts' => 33585,
+ 'Google Play' => 33586,
+ 'Gov.za' => 38328,
+ 'GTA 5' => 37273,
+ 'Guild Wars 2' => 36501,
+ 'Gumtree' => 33592,
+ 'iBurst' => 34620,
+ 'iCloud' => 33587,
+ 'Imaginet' => 38325,
+ 'Instagram' => 33588,
+ 'Internet Solutions' => 38332,
+ 'iTunes' => 33589,
+ 'Kik' => 33590,
+ 'Kraken' => 36985,
+ 'League of Legends' => 38633,
+ 'LinkedIn' => 33591,
+ 'Luno' => 37012,
+ 'Metrofibre' => 38335,
+ 'MTN' => 33601,
+ 'MWEB' => 33606,
+ 'Nedbank' => 35461,
+ 'Neotel' => 35426,
+ 'Netflix' => 36390,
+ 'Octotel' => 38327,
+ 'Office 365' => 35444,
+ 'OLX' => 33255,
+ 'Openserve' => 38331,
+ 'Origin' => 36886,
+ 'Outlook' => 33566,
+ 'Overwatch' => 36149,
+ 'Paypal' => 33567,
+ 'Pinterest' => 33568,
+ 'Player Unknown\'s Battlegrounds' => 36642,
+ 'Playstation Network' => 33569,
+ 'Pokémon Go' => 35756,
+ 'Rain' => 37397,
+ 'Rainbow Six' => 37738,
+ 'Reddit' => 38362,
+ 'Safricom' => 35139,
+ 'SARS' => 38336,
+ 'Seacom' => 38329,
+ 'Showmax' => 37149,
+ 'Skype' => 33570,
+ 'Snapchat' => 33571,
+ 'Standard Bank' => 33598,
+ 'Steam' => 34223,
+ 'Takealot' => 36777,
+ 'Teamviewer' => 37480,
+ 'Telegram' => 37184,
+ 'Telkom' => 33603,
+ 'The elder scrolls online' => 37325,
+ 'The Simpsons Tapped out' => 35903,
+ 'Tinder' => 37166,
+ 'Twitch' => 38702,
+ 'Twitter' => 33572,
+ 'Viber' => 33595,
+ 'Virgin Mobile' => 38324,
+ 'Vodacom' => 33600,
+ 'Vox' => 35368,
+ 'Vumatel' => 37660,
+ 'Warframe' => 37125,
+ 'Webafrica' => 38330,
+ 'WeChat' => 33594,
+ 'Whatsapp' => 33573,
+ 'Wikipedia' => 33574,
+ 'Xbox Live' => 34285,
+ 'Yahoo' => 33575,
+ 'Yahoo Mail' => 33576,
+ 'Youtube' => 33577,
+ ),
+ 'India' => array(
+ 'ACT' => 34764,
+ 'Aircel' => 33257,
+ 'Airtel' => 33233,
+ 'Alexa' => 36921,
+ 'AliExpress' => 37824,
+ 'Amazon' => 35118,
+ 'Amazon Prime Music' => 37583,
+ 'Amazon Prime Video' => 36974,
+ 'Amazon Web Services' => 38411,
+ 'Apex Legends' => 38180,
+ 'App Store' => 38556,
+ 'Apple Store' => 34459,
+ 'Bank of Baroda' => 37676,
+ 'Bank of India' => 33250,
+ 'Bharat Sanchar Nigam Limited (BSNL)' => 33232,
+ 'Binance' => 36932,
+ 'Bitbucket' => 36988,
+ 'Boom Beach' => 34782,
+ 'Brawl Stars' => 38822,
+ 'Call of Duty' => 34153,
+ 'Cherrinet' => 37677,
+ 'Clash of Clans' => 36872,
+ 'Clash Royale' => 38955,
+ 'Cloudflare' => 38652,
+ 'Counter-strike' => 38240,
+ 'Destiny' => 38989,
+ 'Discord' => 38106,
+ 'Dota 2' => 36393,
+ 'Dropbox' => 33237,
+ 'EA' => 34508,
+ 'eBay' => 32863,
+ 'Facebook' => 32860,
+ 'Facebook Messenger' => 33238,
+ 'Facetime' => 34596,
+ 'Fifa' => 38399,
+ 'Flipkart' => 33252,
+ 'Fortnite' => 36843,
+ 'GitHub' => 37606,
+ 'Gmail' => 32862,
+ 'Go Daddy' => 37499,
+ 'Google' => 32857,
+ 'Google Drive' => 38261,
+ 'Google Hangouts' => 32869,
+ 'Google Home' => 37344,
+ 'Google Play' => 33239,
+ 'GTA 5' => 37272,
+ 'Haptik' => 34762,
+ 'Hathway' => 37673,
+ 'Hay Day' => 34787,
+ 'HDFC Bank' => 33231,
+ 'ICICI Bank' => 37674,
+ 'iCloud' => 33240,
+ 'IDBI Bank' => 37678,
+ 'Idea Cellular' => 33234,
+ 'Idian Bank' => 37670,
+ 'iMessage' => 33248,
+ 'Instagram' => 33241,
+ 'IRCTC' => 37671,
+ 'iTunes' => 33230,
+ 'Jio' => 37460,
+ 'Kik' => 33351,
+ 'Line' => 33400,
+ 'LinkedIn' => 33242,
+ 'Mahanagar Telephone Nigam Limited (MTNL)' => 33258,
+ 'Microsoft Azure' => 36112,
+ 'MTS' => 33260,
+ 'Naukri' => 33253,
+ 'Netflix' => 37299,
+ 'Office 365' => 37174,
+ 'OLX' => 33593,
+ 'ooVoo' => 34084,
+ 'Origin' => 38378,
+ 'Outlook' => 33243,
+ 'Paypal' => 33244,
+ 'Paytm' => 33401,
+ 'Pinterest' => 37231,
+ 'Player Unknown\'s Battlegrounds' => 36643,
+ 'Playstation Network' => 32865,
+ 'Pokémon Go' => 35755,
+ 'Quora' => 37473,
+ 'Rainbow Six' => 36412,
+ 'Reddit' => 38061,
+ 'Reliance' => 33236,
+ 'Roblox' => 38921,
+ 'Salesforce' => 34734,
+ 'Sarahah' => 36513,
+ 'Skype' => 32868,
+ 'Snapchat' => 36741,
+ 'Spotify' => 37079,
+ 'Standard Chartered' => 33235,
+ 'State Bank of India (SBI)' => 33251,
+ 'Steam' => 35930,
+ 'Swiggy' => 37675,
+ 'Tango' => 33744,
+ 'Tata Docomo' => 33256,
+ 'Teamviewer' => 34346,
+ 'Telegram' => 36582,
+ 'Tiktok' => 38661,
+ 'Tinder' => 37167,
+ 'Tumblr' => 37641,
+ 'Twitch' => 38355,
+ 'Twitter' => 32861,
+ 'Uber Eats' => 38898,
+ 'Udemy' => 38389,
+ 'Uninor' => 33259,
+ 'Uplay PC' => 36628,
+ 'Viber' => 33049,
+ 'Videocon' => 33261,
+ 'Vimeo' => 37232,
+ 'Vodafone' => 33254,
+ 'Warframe' => 37124,
+ 'Wattpad' => 34698,
+ 'Waze' => 33408,
+ 'Webex' => 34163,
+ 'WeChat' => 33396,
+ 'Whatsapp' => 32867,
+ 'Wikipedia' => 33245,
+ 'Xbox Live' => 32866,
+ 'Yahoo' => 32859,
+ 'Yahoo Mail' => 33246,
+ 'Yahoo Messenger' => 33247,
+ 'You Broadband' => 34763,
+ 'Youtube' => 32858,
+ 'Zee5' => 38647,
+ 'Zerodha' => 37207,
+ 'ZoHo' => 37552,
+ 'Zomato' => 37672,
+ ),
+ 'Portugal' => array(
+ 'ActivoBank' => 33959,
+ 'Apex Legends' => 38127,
+ 'Apple Store' => 34464,
+ 'Banco Espírito Santo' => 33961,
+ 'Banco Santander Totta' => 33960,
+ 'Binance' => 36945,
+ 'Bing' => 33925,
+ 'Blizzard Battle.net' => 37225,
+ 'Cabovisão' => 33956,
+ 'Caixa Geral de Depósitos' => 33957,
+ 'Call of Duty' => 38982,
+ 'Clash Royale' => 38957,
+ 'Counter-Strike' => 36651,
+ 'Dead By Daylight' => 37429,
+ 'Deezer' => 33927,
+ 'Destiny' => 38964,
+ 'Discord' => 37388,
+ 'Dota 2' => 38479,
+ 'EA' => 36452,
+ 'eBay' => 33928,
+ 'Facebook' => 33929,
+ 'Facebook Messenger' => 34847,
+ 'Facetime' => 34586,
+ 'Fifa' => 36905,
+ 'Fortnite' => 36695,
+ 'Gmail' => 33930,
+ 'Go Daddy' => 34849,
+ 'Google' => 33931,
+ 'Google Play' => 33932,
+ 'GTA 5' => 36857,
+ 'HBO' => 38379,
+ 'iCloud' => 33933,
+ 'iMessage' => 33934,
+ 'Instagram' => 33963,
+ 'iTunes' => 33935,
+ 'Kik' => 33943,
+ 'Kraken' => 36980,
+ 'League of Legends' => 38635,
+ 'LinkedIn' => 33936,
+ 'MEO' => 33950,
+ 'Millennium Bcp' => 33958,
+ 'Montepio' => 33962,
+ 'Netflix' => 37301,
+ 'NOS' => 33952,
+ 'Office 365' => 37175,
+ 'OLX' => 33949,
+ 'OneDrive' => 36870,
+ 'Optimus' => 33951,
+ 'Origin' => 36892,
+ 'Outlook' => 33937,
+ 'Overwatch' => 37082,
+ 'Paypal' => 33938,
+ 'Pinterest' => 37373,
+ 'Player Unknown\'s Battlegrounds' => 36566,
+ 'Playstation Network' => 33939,
+ 'Pokémon Go' => 35754,
+ 'Rainbow Six' => 36454,
+ 'Reddit' => 38068,
+ 'Roblox' => 38920,
+ 'Rocket League' => 36668,
+ 'Skype' => 33940,
+ 'Snapchat' => 36742,
+ 'Spotify' => 33964,
+ 'Steam' => 34138,
+ 'Teamviewer' => 35691,
+ 'Telegram' => 37186,
+ 'Tinder' => 37921,
+ 'Twitch' => 36453,
+ 'Twitter' => 33941,
+ 'Uplay PC' => 38651,
+ 'Uzo' => 33954,
+ 'Viber' => 33942,
+ 'Vodafone' => 33953,
+ 'Warframe' => 37135,
+ 'Whatsapp' => 34855,
+ 'Wikipedia' => 33944,
+ 'Xbox Live' => 33945,
+ 'Yahoo' => 33946,
+ 'Yahoo Mail' => 33947,
+ 'Youtube' => 33948,
+ 'Z1 Battle Royale' => 37264,
+ ),
+ 'Schweiz' => array(
+ 'Airbnb' => 37666,
+ 'Anthem' => 38205,
+ 'Apex Legends' => 38130,
+ 'App Store' => 35583,
+ 'Apple Store' => 34462,
+ 'Battlefield' => 38050,
+ 'Bet365' => 38831,
+ 'Binance' => 36935,
+ 'Blizzard Battle.net' => 36569,
+ 'Call of Duty' => 34157,
+ 'Clash Royale' => 38958,
+ 'Coinbase' => 36805,
+ 'Counter-strike' => 36646,
+ 'Crunchyroll' => 38144,
+ 'Dazn' => 36509,
+ 'Dead By Daylight' => 37413,
+ 'Deezer' => 34038,
+ 'Destiny' => 36591,
+ 'Discord' => 37389,
+ 'Dota 2' => 35402,
+ 'Dropbox' => 34039,
+ 'EA' => 34503,
+ 'eBay' => 34040,
+ 'Epic Games Store' => 39026,
+ 'Evard' => 35642,
+ 'Facebook' => 34041,
+ 'Facebook Messenger' => 34885,
+ 'Facetime' => 34585,
+ 'Fifa' => 37089,
+ 'flashcable' => 37202,
+ 'Flickr' => 34042,
+ 'For Honor' => 35997,
+ 'Fortnite' => 36688,
+ 'Ghost Recon' => 36006,
+ 'Gmail' => 34043,
+ 'GMX' => 34044,
+ 'Google' => 34045,
+ 'Google Hangouts' => 34046,
+ 'Google Play' => 34047,
+ 'Green' => 36971,
+ 'Grindr' => 38742,
+ 'GTA 5' => 35502,
+ 'Guild Wars 2' => 36465,
+ 'Hay Day' => 34853,
+ 'iCloud' => 34048,
+ 'ICQ' => 34049,
+ 'iMessage' => 34050,
+ 'Instagram' => 34051,
+ 'iTunes' => 34052,
+ 'Kik' => 34054,
+ 'Kraken' => 36807,
+ 'League of Legends' => 35574,
+ 'LinkedIn' => 34055,
+ 'Lovoo' => 35401,
+ 'Mail.de' => 38629,
+ 'Netatmo' => 38467,
+ 'Netflix' => 34632,
+ 'Nitrado' => 35547,
+ 'Office 365' => 36581,
+ 'OneDrive' => 35413,
+ 'Origin' => 36891,
+ 'Outlook' => 34057,
+ 'Overwatch' => 36152,
+ 'Peoplefone' => 36602,
+ 'Playerunknown\'s Battlegrounds' => 36560,
+ 'Playstation Network' => 34087,
+ 'Pokémon Go' => 35744,
+ 'PostFinance' => 36048,
+ 'Protonmail' => 35643,
+ 'Quickline' => 36970,
+ 'Quizduell' => 34529,
+ 'Rainbow Six' => 36147,
+ 'Red Dead Redemption' => 37741,
+ 'Reddit' => 38067,
+ 'Ricardo' => 34079,
+ 'Rocket League' => 35486,
+ 'Salt' => 35602,
+ 'Search.ch' => 34080,
+ 'Sky Sport' => 37069,
+ 'Skype' => 34059,
+ 'Snapchat' => 34060,
+ 'Spotify' => 34061,
+ 'SRF' => 34081,
+ 'Steam' => 34226,
+ 'Sunrise' => 34078,
+ 'Swisscom' => 34077,
+ 'Tango' => 34062,
+ 'Teamviewer' => 34616,
+ 'Telegram' => 35968,
+ 'The elder scrolls online' => 35763,
+ 'Threema' => 34256,
+ 'Tinder' => 34244,
+ 'Tumblr' => 34063,
+ 'TuneIn' => 38775,
+ 'Tutti' => 36014,
+ 'Tweakbox' => 38904,
+ 'Twint' => 38183,
+ 'Twitch' => 35505,
+ 'Twitter' => 34064,
+ 'UBS' => 34082,
+ 'UPC' => 34075,
+ 'Uplay PC' => 34690,
+ 'Viber' => 34065,
+ 'Viewster' => 34325,
+ 'Vimeo' => 34066,
+ 'Waze' => 34067,
+ 'Web.de' => 34068,
+ 'Whatsapp' => 34069,
+ 'Wikipedia' => 34070,
+ 'World of Warships' => 38015,
+ 'Xbox Live' => 34088,
+ 'Yahoo Mail' => 34072,
+ 'Yahoo Messenger' => 34073,
+ 'Yallo' => 37298,
+ 'Youtube' => 34074,
+ 'Z1 Battle Royale' => 35492,
+ 'Zattoo' => 35366,
+ ),
+ 'Singapore' => array(
+ 'Airbnb' => 37608,
+ 'Apex Legends' => 38182,
+ 'App Store' => 37735,
+ 'Apple Store' => 34682,
+ 'Binance' => 36944,
+ 'Bing' => 34652,
+ 'Blizzard Battle.net' => 36431,
+ 'Brawl Stars' => 38820,
+ 'Call of Duty' => 39051,
+ 'Clash of Clans' => 34667,
+ 'Clash Royale' => 38952,
+ 'Counter-strike' => 36556,
+ 'DBS' => 34658,
+ 'Destiny' => 38986,
+ 'Discord' => 37100,
+ 'Dota 2' => 35875,
+ 'Dropbox' => 34671,
+ 'EA' => 36429,
+ 'Facebook' => 34645,
+ 'Facebook Messenger' => 34646,
+ 'Facetime' => 34681,
+ 'Fifa' => 38398,
+ 'Fortnite' => 37321,
+ 'Ghost Recon' => 38995,
+ 'Gmail' => 34647,
+ 'Google' => 34648,
+ 'Google Drive' => 34649,
+ 'Google Hangouts' => 38364,
+ 'Google Play' => 38519,
+ 'Grindr' => 36754,
+ 'GTA 5' => 37278,
+ 'HSBC' => 34672,
+ 'iCloud' => 34685,
+ 'iMessage' => 34684,
+ 'Instagram' => 34665,
+ 'iTunes' => 34683,
+ 'League of Legends' => 38748,
+ 'Line' => 34740,
+ 'LinkedIn' => 34656,
+ 'M1' => 34662,
+ 'Microsoft Azure' => 36113,
+ 'Minecraft' => 38738,
+ 'My Republic' => 36463,
+ 'Netflix' => 36391,
+ 'Office 365' => 37173,
+ 'OkCupid' => 38490,
+ 'Origin' => 38377,
+ 'Outlook' => 34673,
+ 'Overwatch' => 36389,
+ 'Path of Exile' => 37723,
+ 'Player Unknown\'s Battlegrounds' => 36361,
+ 'Playstation Network' => 34668,
+ 'Pokémon Go' => 35757,
+ 'POSB' => 34738,
+ 'Rainbow Six' => 36382,
+ 'Reddit' => 37475,
+ 'Roblox' => 37286,
+ 'SingTel' => 34661,
+ 'Skype' => 36418,
+ 'Snapchat' => 34666,
+ 'Spotify' => 34739,
+ 'Standard Chartered' => 34743,
+ 'Starhub' => 34663,
+ 'Steam' => 36430,
+ 'Summoners War' => 37421,
+ 'Taobao' => 34660,
+ 'Telegram' => 36381,
+ 'Tinder' => 37137,
+ 'Tumblr' => 36711,
+ 'Tweakbox' => 38345,
+ 'Twitch' => 36539,
+ 'Twitter' => 34659,
+ 'Uplay PC' => 37521,
+ 'Viber' => 34670,
+ 'Viewqwest' => 37506,
+ 'Warframe' => 36494,
+ 'WeChat' => 34674,
+ 'Whatsapp' => 34664,
+ 'Whisper' => 34624,
+ 'Wikipedia' => 34655,
+ 'Xbox Live' => 34669,
+ 'Yahoo' => 34654,
+ 'Yahoo Mail' => 34653,
+ 'Youtube' => 34650,
+ ),
+ 'Türkiye' => array(
+ 'Akbank' => 33783,
+ 'Anthem' => 38195,
+ 'Apex Legends' => 38121,
+ 'Apple Store' => 34451,
+ 'Battlefield' => 38449,
+ 'Binance' => 36952,
+ 'Blizzard Battle.net' => 37224,
+ 'Call of Duty' => 38940,
+ 'Counter-strike' => 36652,
+ 'D-Smart' => 34422,
+ 'Dead By Daylight' => 37433,
+ 'Denizbank' => 33788,
+ 'Destiny' => 38984,
+ 'Discord' => 36766,
+ 'Dota 2' => 36396,
+ 'EA' => 36157,
+ 'Facebook' => 33748,
+ 'Facebook Messenger' => 33749,
+ 'Facetime' => 34588,
+ 'Fifa' => 37087,
+ 'Finansbank' => 33786,
+ 'For Honor' => 37369,
+ 'Fortnite' => 36698,
+ 'Garanti' => 33780,
+ 'GittiGidiyor' => 33779,
+ 'Gmail' => 33750,
+ 'Google' => 33751,
+ 'Google Hangouts' => 33752,
+ 'Google Play' => 33753,
+ 'Gran Turismo' => 36947,
+ 'GTA 5' => 37276,
+ 'HalkBank' => 33784,
+ 'HSBC' => 33790,
+ 'iCloud' => 33754,
+ 'iMessage' => 33755,
+ 'ING Bank' => 33789,
+ 'Instagram' => 33732,
+ 'iTunes' => 33756,
+ 'Kik' => 33757,
+ 'Kraken' => 36986,
+ 'LinkedIn' => 33758,
+ 'Messageme' => 33727,
+ 'Netflix' => 37300,
+ 'Office 365' => 38058,
+ 'Origin' => 36901,
+ 'Outlook' => 33759,
+ 'Overwatch' => 36386,
+ 'Player Unknown\'s Battlegrounds' => 36456,
+ 'Playstation Network' => 33760,
+ 'Rainbow Six' => 36154,
+ 'Reddit' => 38064,
+ 'Roblox' => 38915,
+ 'Rocket League' => 36669,
+ 'Sahibinden' => 33778,
+ 'Skype' => 33761,
+ 'Snapchat' => 33762,
+ 'Steam' => 37322,
+ 'Tango' => 33730,
+ 'Telegram' => 37090,
+ 'Tinder' => 37911,
+ 'Ttnet' => 33776,
+ 'Türk Ekonomi Bankası (TEB)' => 33791,
+ 'Türk Telekom' => 33771,
+ 'Turkcell' => 33774,
+ 'Türkiye İş Bankası' => 33781,
+ 'Türksat Kablo' => 33772,
+ 'Twitch' => 35506,
+ 'Twitter' => 33613,
+ 'Uplay PC' => 36156,
+ 'VakıfBank' => 33785,
+ 'Viber' => 33733,
+ 'Vodafone' => 33775,
+ 'Warframe' => 37128,
+ 'Whatsapp' => 33764,
+ 'Xbox Live' => 33766,
+ 'Yahoo Mail' => 38885,
+ 'Yandex' => 33777,
+ 'Yapı Kredi' => 33782,
+ 'Youtube' => 33767,
+ 'Ziraat Bankası' => 33787,
+ ),
+ 'Suomi' => array(
+ 'Aktia' => 36308,
+ 'Apex Legends' => 38123,
+ 'Battlefield' => 37096,
+ 'Binance' => 36929,
+ 'Blizzard Battle.net' => 36299,
+ 'Call of Duty' => 36706,
+ 'Clash Royale' => 38947,
+ 'Counter-strike' => 36645,
+ 'Crunchyroll' => 38097,
+ 'Dankse Bank' => 36307,
+ 'Dead By Daylight' => 37428,
+ 'Destiny' => 38531,
+ 'Discord' => 36681,
+ 'DNA' => 36304,
+ 'Dota 2' => 36434,
+ 'EA' => 36295,
+ 'Elisa' => 36303,
+ 'Epic Games Store' => 39030,
+ 'Escape from Tarkov' => 39057,
+ 'Facebook' => 36237,
+ 'Facebook Messenger' => 36240,
+ 'Faceit' => 39038,
+ 'Fifa' => 37603,
+ 'Fortnite' => 36691,
+ 'Ghost Recon' => 38998,
+ 'Gmail' => 36254,
+ 'Google' => 36253,
+ 'Google Play' => 38522,
+ 'Gran Turismo' => 36912,
+ 'GTA 5' => 36844,
+ 'Guild Wars 2' => 36471,
+ 'HBO Nordic' => 36302,
+ 'iCloud' => 38841,
+ 'Instagram' => 36435,
+ 'Kraken' => 36852,
+ 'League of Legends' => 38632,
+ 'Minecraft' => 38616,
+ 'Netflix' => 36252,
+ 'Nordea' => 36306,
+ 'Office 365' => 36297,
+ 'OP' => 36305,
+ 'Origin' => 36904,
+ 'Outlook' => 36251,
+ 'Overwatch' => 36250,
+ 'Path of Exile' => 36530,
+ 'Paypal' => 37347,
+ 'Playerunknown\'s Battlegrounds' => 36339,
+ 'Playstation Network' => 36249,
+ 'Pokémon Go' => 36248,
+ 'Rainbow Six' => 36247,
+ 'Reddit' => 36823,
+ 'Roblox' => 38913,
+ 'Rocket League' => 36300,
+ 'Runescape' => 38655,
+ 'Sea of Thieves' => 37118,
+ 'Skype' => 36246,
+ 'Slack' => 37496,
+ 'Snapchat' => 36245,
+ 'Spotify' => 37078,
+ 'Steam' => 36296,
+ 'Telegram' => 37091,
+ 'Telia' => 36287,
+ 'Tinder' => 36298,
+ 'Twitch' => 36436,
+ 'Twitter' => 36677,
+ 'Uplay PC' => 36244,
+ 'Viaplay' => 37294,
+ 'Viber' => 37494,
+ 'Warframe' => 36704,
+ 'Whatsapp' => 36243,
+ 'Wikipedia' => 38871,
+ 'World of Tanks' => 36673,
+ 'Xbox Live' => 36301,
+ 'Yahoo Mail' => 38883,
+ 'Youtube' => 36242,
+ 'Z1 Battle Royale' => 37259,
+ ),
+ 'France' => array(
+ 'Albion Online' => 38796,
+ 'Alexa' => 38030,
+ 'Alice' => 34009,
+ 'Amazon' => 32693,
+ 'Amazon Web Services' => 38109,
+ 'Ameli' => 38705,
+ 'Amen' => 35888,
+ 'Anthem' => 38207,
+ 'Apex Legends' => 38116,
+ 'App Store' => 35582,
+ 'Apple Store' => 34469,
+ 'AXA Banque' => 33427,
+ 'Bankin\'' => 37592,
+ 'Banque Populaire' => 33432,
+ 'Battlefield' => 38057,
+ 'Betclic' => 39046,
+ 'Binance' => 36939,
+ 'Bing' => 32696,
+ 'BlaBlaCar' => 36089,
+ 'Blizzard Battle.net' => 36437,
+ 'Blogger' => 32697,
+ 'BNP Paribas' => 32749,
+ 'Boom Beach' => 35154,
+ 'Bouygues Télécom' => 32747,
+ 'Brawl Stars' => 38815,
+ 'Caisse d\'allocations familiales' => 38708,
+ 'Caisse d\'Epargne' => 33428,
+ 'Call of Duty' => 35037,
+ 'CanalSat' => 34034,
+ 'Candy Crush' => 35881,
+ 'Cdiscount' => 35038,
+ 'CIC' => 33431,
+ 'Clash Royale' => 38151,
+ 'Cloudflare' => 38622,
+ 'Coinbase' => 36830,
+ 'Completel' => 33982,
+ 'Compte Nickel' => 35983,
+ 'Counter-Strike' => 36649,
+ 'Crédit Agricole' => 32753,
+ 'Crédit Mutuel' => 33429,
+ 'Crunchyroll' => 38096,
+ 'Dartybox' => 32848,
+ 'Dead By Daylight' => 37425,
+ 'Deezer' => 32843,
+ 'Destiny' => 34951,
+ 'Discord' => 36763,
+ 'Dofus Touch' => 38711,
+ 'Dota 2' => 35877,
+ 'Dropbox' => 32700,
+ 'Duel Quiz' => 34530,
+ 'EA' => 32844,
+ 'eBay' => 32701,
+ 'Elite: Dangerous' => 37776,
+ 'Epic Games Store' => 39029,
+ 'Escape from Tarkov' => 39058,
+ 'Facebook' => 32702,
+ 'Facebook Messenger' => 32703,
+ 'Facetime' => 34602,
+ 'Fallout' => 37667,
+ 'Fifa' => 35475,
+ 'Flickr' => 32704,
+ 'Fnac' => 35065,
+ 'For Honor' => 35995,
+ 'Fortnite' => 36656,
+ 'Free' => 32744,
+ 'Gandi' => 38712,
+ 'Ghost Recon' => 38959,
+ 'GitHub' => 32705,
+ 'Gmail' => 32706,
+ 'Google' => 32707,
+ 'Google Agenda' => 38601,
+ 'Google Drive' => 36608,
+ 'Google Hangouts' => 32709,
+ 'Google Play' => 32708,
+ 'Gran Turismo' => 36911,
+ 'Grindr' => 36756,
+ 'GTA 5' => 35039,
+ 'Guild Wars 2' => 36468,
+ 'Hearthstone' => 38562,
+ 'Hootsuite' => 32710,
+ 'Hue' => 37815,
+ 'Hunt: showdown' => 38824,
+ 'iCloud' => 32712,
+ 'Idealo' => 34890,
+ 'iMessage' => 32713,
+ 'ING Direct' => 33426,
+ 'Instagram' => 32715,
+ 'iTunes' => 32716,
+ 'JeuxVidéo' => 32847,
+ 'K-net' => 37790,
+ 'Kraken' => 36753,
+ 'La Banque Postale' => 32754,
+ 'La Poste' => 37215,
+ 'La Poste Mobile' => 32752,
+ 'LCL (Crédit Lyonnais)' => 33424,
+ 'Le Bon Coin' => 32840,
+ 'League of Legends' => 35369,
+ 'LinkedIn' => 32717,
+ 'LycaMobile' => 32849,
+ 'M6 Mobile' => 32845,
+ 'Magic' => 37456,
+ 'Météo France' => 38706,
+ 'Microsoft Azure' => 36115,
+ 'Minecraft' => 32718,
+ 'Molotov.TV' => 35965,
+ 'myCanal' => 38710,
+ 'Netatmo' => 37957,
+ 'Netflix' => 34633,
+ 'Nintendo eShop' => 34103,
+ 'Nordnet' => 38709,
+ 'NRJ Mobile' => 32846,
+ 'Numéricable' => 32748,
+ 'OCS' => 38707,
+ 'Office 365' => 35126,
+ 'Onedrive' => 35409,
+ 'Online.net' => 36159,
+ 'Orange' => 32745,
+ 'Orange Bank' => 37511,
+ 'Origin' => 36896,
+ 'Outlook' => 32711,
+ 'Overwatch' => 36151,
+ 'OVH' => 34744,
+ 'Paladins' => 36378,
+ 'Path of Exile' => 36855,
+ 'Paypal' => 32842,
+ 'Photobucket' => 32721,
+ 'Pinterest' => 32722,
+ 'Player Unknown\'s Battlegrounds' => 36363,
+ 'Playstation Network' => 32741,
+ 'Pokémon Go' => 35735,
+ 'Prime Video' => 38457,
+ 'Rainbow Six' => 35562,
+ 'Rakuten TV' => 37596,
+ 'Realm Royale' => 37308,
+ 'Red Dead Redemption' => 38287,
+ 'Reddit' => 37368,
+ 'Roblox' => 38755,
+ 'Rocket League' => 35253,
+ 'Salesforce' => 38501,
+ 'Sea of Thieves' => 37117,
+ 'SFR' => 32746,
+ 'Shadow' => 37212,
+ 'Skype' => 32723,
+ 'Skyrock.com' => 33430,
+ 'Slack' => 37337,
+ 'Slideshare' => 32724,
+ 'Snapchat' => 33378,
+ 'Société Générale' => 33425,
+ 'Sosh' => 34830,
+ 'Spotify' => 32727,
+ 'Star Citizen' => 39037,
+ 'Steam' => 32742,
+ 'Streamlabs' => 38927,
+ 'Syma' => 37449,
+ 'Tango' => 34482,
+ 'Teamviewer' => 34908,
+ 'Telegram' => 34230,
+ 'The elder scrolls online' => 37326,
+ 'Tinder' => 34808,
+ 'Tumblr' => 32728,
+ 'TuneIn' => 38758,
+ 'Tweakbox' => 38347,
+ 'Twitch' => 35027,
+ 'Twitter' => 32729,
+ 'Uber Eats' => 38897,
+ 'Unibet' => 38274,
+ 'Uplay PC' => 35544,
+ 'Viber' => 33373,
+ 'Vimeo' => 32730,
+ 'Warface' => 38776,
+ 'Warframe' => 36368,
+ 'Waze' => 33410,
+ 'WeTransfer' => 32731,
+ 'Whatsapp' => 32575,
+ 'Wibox' => 37055,
+ 'Wikipedia' => 32732,
+ 'Wordpress.com' => 32734,
+ 'World of Tanks' => 36030,
+ 'Xbox Live' => 32743,
+ 'Yahoo' => 32735,
+ 'Yahoo Mail' => 32736,
+ 'Yahoo Messenger' => 32737,
+ 'Youtube' => 32739,
+ 'Z1 Battle Royale' => 37260,
+ 'Zynga' => 32740,
+ ),
+ 'Brasil' => array(
+ 'Albion Online' => 38797,
+ 'Alelo' => 37410,
+ 'Algar' => 37507,
+ 'Alog' => 34746,
+ 'Amazon' => 33206,
+ 'Amazon Prime Video' => 38754,
+ 'Amazon Web Services' => 34091,
+ 'America Net' => 35127,
+ 'Anthem' => 38211,
+ 'Anydesk' => 37492,
+ 'Apex Legends' => 38126,
+ 'App Store' => 39054,
+ 'Apple Store' => 34449,
+ 'Avianca' => 36519,
+ 'Azul' => 36358,
+ 'Banco Central do Brasil' => 36002,
+ 'Banco do Brasil' => 34037,
+ 'Banco Inter' => 37559,
+ 'Banco Itaú' => 33205,
+ 'Banco Safra' => 37151,
+ 'Banco Santander' => 33381,
+ 'Banestes' => 37065,
+ 'Banrisul' => 35425,
+ 'Battlefield' => 38447,
+ 'Betfair' => 38188,
+ 'Binance' => 36940,
+ 'Bing' => 33215,
+ 'Blizzard Battle.net' => 36671,
+ 'Bradesco' => 33197,
+ 'Brisanet' => 36967,
+ 'Buscapé' => 35167,
+ 'C6 Bank' => 38773,
+ 'Cabo Telecom' => 33991,
+ 'Cabonnet' => 35919,
+ 'Caixa Econômica Federal' => 33191,
+ 'Call of Duty' => 38163,
+ 'Claro' => 33199,
+ 'Clash of Clans' => 37303,
+ 'Clash Royale' => 36053,
+ 'Clear' => 37557,
+ 'Cloudflare' => 38621,
+ 'Clusterweb' => 35967,
+ 'Copel Telecom' => 35671,
+ 'Correios' => 34611,
+ 'Counter-Strike' => 38162,
+ 'Credit Suisse' => 37978,
+ 'Crunchyroll' => 37138,
+ 'Dataprev' => 35137,
+ 'Dead By Daylight' => 36596,
+ 'Deezer' => 33385,
+ 'Destiny' => 38943,
+ 'Discord' => 37392,
+ 'Dota 2' => 35879,
+ 'Dropbox' => 33214,
+ 'EA' => 34500,
+ 'eBay' => 33207,
+ 'eCAC' => 34961,
+ 'Embratel' => 33999,
+ 'Enem' => 35136,
+ 'Epic Games Store' => 39031,
+ 'eSocial' => 35427,
+ 'Faceapp' => 38696,
+ 'Facebook' => 33184,
+ 'Facebook Messenger' => 34846,
+ 'Facetime' => 34597,
+ 'Feedly' => 34723,
+ 'Fifa' => 37769,
+ 'For Honor' => 37371,
+ 'Fortnite' => 36699,
+ 'Free Fire' => 38804,
+ 'Garena' => 38301,
+ 'Getnet' => 36745,
+ 'GitHub' => 38591,
+ 'Globo' => 34721,
+ 'Gmail' => 33194,
+ 'Go Daddy' => 34848,
+ 'Gol' => 38600,
+ 'Google' => 33186,
+ 'Google Cloud' => 38535,
+ 'Google Play' => 33211,
+ 'GTA 5' => 34757,
+ 'GVT' => 33562,
+ 'HBO' => 36354,
+ 'Hostgator' => 34745,
+ 'Hostnet' => 35850,
+ 'HSBC' => 34644,
+ 'iCloud' => 33219,
+ 'ICQ' => 34765,
+ 'iFood ' => 36960,
+ 'iMessage' => 33165,
+ 'Instagram' => 33204,
+ 'ITMNetworks' => 36094,
+ 'iTunes' => 33208,
+ 'Jurassic World Alive' => 37335,
+ 'Kik' => 34856,
+ 'KingHost' => 34957,
+ 'Kraken' => 36979,
+ 'League of Legends' => 39018,
+ 'Ligue Telecom' => 37526,
+ 'Line' => 33736,
+ 'LinkedIn' => 33210,
+ 'Locaweb' => 34722,
+ 'Mandic' => 36090,
+ 'Mercado Bitcoin' => 36790,
+ 'Mercado Livre' => 34234,
+ 'Microsoft Azure' => 36111,
+ 'Multiplay' => 37221,
+ 'NET' => 33190,
+ 'Netflix' => 33222,
+ 'Neverwinter' => 36158,
+ 'Nextel' => 33202,
+ 'Nota fiscal eletrônica' => 34718,
+ 'Nubank' => 37063,
+ 'Office 365' => 37170,
+ 'Oi' => 33196,
+ 'OLX' => 34235,
+ 'OneDrive' => 36866,
+ 'Origin' => 36903,
+ 'Outlook' => 33221,
+ 'Overwatch' => 36502,
+ 'PagSeguro' => 37313,
+ 'Path of Exile' => 37725,
+ 'Paypal' => 33213,
+ 'Pinterest' => 38164,
+ 'Player Unknown\'s Battlegrounds' => 36565,
+ 'Playstation Network' => 33217,
+ 'Pokémon Go' => 35751,
+ 'Polícia Federal' => 35135,
+ 'Porto Seguro Conecta' => 35981,
+ 'QConcursos' => 36601,
+ 'Rainbow Six' => 36451,
+ 'Receita Federal' => 34960,
+ 'Red Dead Redemption' => 38909,
+ 'Reddit' => 37477,
+ 'Roblox' => 37399,
+ 'Rocket League' => 38558,
+ 'Salesforce' => 38494,
+ 'Sefaz' => 37626,
+ 'Sercomtel' => 33990,
+ 'Sicoob' => 37624,
+ 'Sicredi' => 37505,
+ 'SiSU' => 38029,
+ 'SKY' => 33875,
+ 'Skype' => 33203,
+ 'Slack' => 37339,
+ 'Snapchat' => 33379,
+ 'Spotify' => 36594,
+ 'Steam' => 34137,
+ 'Submarino' => 35074,
+ 'SuperDigital' => 36744,
+ 'Teamviewer' => 35690,
+ 'Telegram' => 34937,
+ 'Terra' => 33193,
+ 'TIM' => 34686,
+ 'Tinder' => 36550,
+ 'Tribunal Superior Eleitoral' => 37578,
+ 'Twitch' => 36372,
+ 'Twitter' => 33195,
+ 'Uber' => 37767,
+ 'Udemy' => 38313,
+ 'Umbler' => 37577,
+ 'UOL' => 33189,
+ 'UOLHost' => 34748,
+ 'Uplay PC' => 38636,
+ 'Viber' => 33386,
+ 'Vimeo' => 38533,
+ 'Vivo' => 33192,
+ 'Vono' => 35138,
+ 'Warframe' => 36702,
+ 'Waze' => 33383,
+ 'WeChat' => 33735,
+ 'Whatsapp' => 32837,
+ 'Wikipedia' => 33198,
+ 'World of Warcraft' => 38879,
+ 'Xbox Live' => 33216,
+ 'Yahoo' => 33187,
+ 'Yahoo Mail' => 33201,
+ 'Youtube' => 33185,
+ 'Zello' => 33387,
+ ),
+ 'Россия' => array(
+ 'Albion Online' => 38798,
+ 'Anthem' => 38191,
+ 'Apex Legends' => 38138,
+ 'Apple Music' => 39012,
+ 'Apple Store' => 34470,
+ 'avito' => 37696,
+ 'Battlefield' => 38448,
+ 'Binance' => 37021,
+ 'Blizzard Battle.net' => 36784,
+ 'Call of Duty' => 39052,
+ 'Citilink' => 37700,
+ 'Cloudflare' => 38619,
+ 'Counter-strike' => 38234,
+ 'Dead By Daylight' => 37430,
+ 'Destiny' => 38941,
+ 'DNS Shop' => 37701,
+ 'Dota 2' => 36395,
+ 'EA' => 36924,
+ 'eBay' => 32799,
+ 'Elite: Dangerous' => 37775,
+ 'Facetime' => 34599,
+ 'Fifa' => 38428,
+ 'For Honor' => 37370,
+ 'Fortnite' => 37143,
+ 'GitHub' => 38713,
+ 'Gmail' => 32798,
+ 'GTA 5' => 36845,
+ 'iCloud' => 38840,
+ 'ICQ' => 33122,
+ 'iMessage' => 33115,
+ 'Interzet' => 33563,
+ 'iTunes' => 33114,
+ 'Ivi' => 34807,
+ 'Kraken' => 36982,
+ 'Last FM' => 36533,
+ 'Mail.Ru' => 33113,
+ 'Megogo' => 38198,
+ 'NetByNet' => 35927,
+ 'Okko' => 38793,
+ 'Origin' => 36900,
+ 'Outlook' => 33116,
+ 'Overwatch' => 36385,
+ 'Ozon' => 37702,
+ 'Path of Exile' => 37724,
+ 'Paypal' => 33118,
+ 'Player Unknown\'s Battlegrounds' => 36455,
+ 'Playstation Network' => 32801,
+ 'Qip' => 37697,
+ 'Qiwi' => 33504,
+ 'Rainbow Six' => 36457,
+ 'Reddit' => 38066,
+ 'Roblox' => 38922,
+ 'SkyNet' => 35103,
+ 'Slack' => 37340,
+ 'Snapchat' => 37144,
+ 'Teamviewer' => 34347,
+ 'Telegram' => 36734,
+ 'The elder scrolls online' => 37323,
+ 'Tumblr' => 37284,
+ 'Twitter' => 32797,
+ 'Uplay PC' => 35611,
+ 'Viber ' => 33402,
+ 'Warframe' => 37126,
+ 'WebMoney' => 33119,
+ 'Wildberries' => 37699,
+ 'World of Tanks' => 35051,
+ 'Xbox Live' => 32802,
+ 'Yahoo' => 32792,
+ 'Yahoo Mail' => 32793,
+ 'Yahoo Messenger' => 32794,
+ 'Yota' => 34356,
+ 'Акадо' => 34429,
+ 'Альфа-Банк' => 33110,
+ 'Банк ДОМ.РФ' => 38704,
+ 'Билайн' => 32850,
+ 'Ватсап' => 32803,
+ 'Википедия' => 33120,
+ 'ВКонтакте' => 32851,
+ 'ВТБ 24' => 33109,
+ 'ГИС ЖКХ' => 35822,
+ 'Гугл' => 32788,
+ 'Гугл Hangouts' => 32789,
+ 'Гугл Плей' => 32790,
+ 'Дискорд ' => 37386,
+ 'Дом.ru' => 34395,
+ 'Инстаграм' => 36069,
+ 'Кинопаб' => 38199,
+ 'Летай' => 34430,
+ 'МГТС' => 33108,
+ 'МегаФон' => 33104,
+ 'Мотив' => 33864,
+ 'МТС' => 33121,
+ 'НСПК ' => 35608,
+ 'Одноклассники' => 33112,
+ 'Почта России' => 36587,
+ 'Рамблер' => 37441,
+ 'Релком' => 34357,
+ 'Росреестр' => 38311,
+ 'Ростелеком' => 33105,
+ 'Сбербанк' => 33106,
+ 'СДЭК' => 38729,
+ 'Скай Линк' => 34358,
+ 'Скайп' => 32804,
+ 'Стим' => 34266,
+ 'Твич' => 36543,
+ 'Теле2' => 33818,
+ 'Тиндер' => 37919,
+ 'Тинькофф Банк ' => 37698,
+ 'ТТК' => 34359,
+ 'Уфанет' => 34431,
+ 'Фейсбук' => 32795,
+ 'Фейсбук Мессенджер' => 32796,
+ 'ФНС' => 38648,
+ 'Хоум Кредит' => 38627,
+ 'ЭлЖур ' => 37515,
+ 'Ютуб' => 32791,
+ 'Яндекс' => 33111,
+ 'Яндекс.Музыка' => 39013,
+ 'Яндекс.Навигатор' => 39014,
+ ),
+ 'España' => array(
+ 'Alexa' => 38032,
+ 'Amazon' => 33140,
+ 'Amazon Prime Video' => 38753,
+ 'Anthem' => 38201,
+ 'Anydesk' => 37490,
+ 'Apex Legends' => 38122,
+ 'App Store' => 38553,
+ 'Apple Store' => 34465,
+ 'Banco Popular' => 33135,
+ 'Banco Sabadell' => 33151,
+ 'Banco Santander' => 33132,
+ 'Bankia' => 33134,
+ 'Bankinter' => 33143,
+ 'Battlefield' => 39017,
+ 'BBVA' => 33133,
+ 'Binance' => 36936,
+ 'Blizzard Battle.net' => 36105,
+ 'Brawl Stars' => 38832,
+ 'Cableworld' => 37457,
+ 'Call of Duty' => 35538,
+ 'Clash of Clans' => 34362,
+ 'Clash Royale' => 38951,
+ 'Coinbase' => 36803,
+ 'Counter Strike' => 38239,
+ 'Crunchyroll' => 38147,
+ 'Dazn' => 39005,
+ 'Dead By Daylight' => 36597,
+ 'Deezer' => 33830,
+ 'Destiny' => 38944,
+ 'Discord' => 37387,
+ 'Dota 2' => 37188,
+ 'Dropbox' => 33142,
+ 'EA' => 36449,
+ 'eBay' => 33267,
+ 'Epic Games Store' => 39032,
+ 'Euskaltel' => 34442,
+ 'Facebook' => 32829,
+ 'Facebook Messenger' => 32830,
+ 'Facetime' => 34600,
+ 'Fifa' => 37088,
+ 'For Honor' => 36182,
+ 'Fortnite' => 36694,
+ 'Ghost Recon' => 38996,
+ 'Github' => 36521,
+ 'Gmail' => 32832,
+ 'Google' => 32822,
+ 'Google Drive' => 36605,
+ 'Google Hangouts' => 32823,
+ 'Google Play' => 33226,
+ 'Gran Turismo' => 36950,
+ 'Grindr' => 38401,
+ 'GTA 5' => 37274,
+ 'Guild Wars 2' => 36485,
+ 'HBO' => 36497,
+ 'Ibercaja' => 33153,
+ 'iCloud' => 33227,
+ 'iMessage' => 32980,
+ 'ING Direct' => 33148,
+ 'Instagram' => 33147,
+ 'iTunes' => 33144,
+ 'Jazztel' => 33129,
+ 'Kraken' => 36806,
+ 'League of Legends' => 38634,
+ 'Line' => 33394,
+ 'LinkedIn' => 33150,
+ 'Llamaya' => 38315,
+ 'Lowi' => 35832,
+ 'MásMóvil' => 36068,
+ 'Mil Anuncios' => 33141,
+ 'Movistar' => 33124,
+ 'Nest' => 38551,
+ 'Netflix' => 35565,
+ 'Office 365' => 35442,
+ 'OneDrive' => 36864,
+ 'ONO' => 33128,
+ 'Orange' => 33126,
+ 'Origin' => 36895,
+ 'Outlook' => 33220,
+ 'Overwatch' => 36387,
+ 'Pasion.com' => 37141,
+ 'Path of Exile' => 37770,
+ 'Paypal' => 33145,
+ 'Pepephone' => 33130,
+ 'Player Unknown\'s Battlegrounds' => 36561,
+ 'Playstation Network' => 32835,
+ 'Pokémon Go' => 35750,
+ 'Quantis' => 37050,
+ 'R' => 34441,
+ 'Rainbow Six' => 36145,
+ 'Rakuten TV' => 37595,
+ 'Reddit' => 37476,
+ 'Roblox' => 38928,
+ 'Rocket League' => 36181,
+ 'Sea of Thieves' => 37119,
+ 'Segunda Mano' => 33138,
+ 'Simyo' => 33131,
+ 'Sky' => 37520,
+ 'Skype' => 32838,
+ 'Slack' => 37342,
+ 'Snapchat' => 33380,
+ 'Spotify' => 33146,
+ 'Steam' => 34280,
+ 'Tango' => 33746,
+ 'Teamviewer' => 35688,
+ 'Telecable' => 34443,
+ 'Telegram' => 35352,
+ 'Tinder' => 36548,
+ 'Tuenti' => 33137,
+ 'Tweakbox' => 38350,
+ 'Twitch' => 36545,
+ 'Twitter' => 32831,
+ 'Unicaja' => 33149,
+ 'Uplay PC' => 35615,
+ 'Vibbo' => 36183,
+ 'Viber' => 33374,
+ 'Vodafone' => 33125,
+ 'Warframe' => 36705,
+ 'Whatsapp' => 33263,
+ 'Wikipedia' => 33139,
+ 'Xbox Live' => 32836,
+ 'Yahoo' => 32826,
+ 'Yahoo Mail' => 32827,
+ 'Yahoo Messenger' => 32828,
+ 'Yoigo' => 33127,
+ 'Youtube' => 32825,
+ 'Z1 Battle Royale' => 37263,
+ ),
+ 'Polska' => array(
+ 'Allegro' => 33799,
+ 'Amazon' => 33633,
+ 'Apex Legends' => 38124,
+ 'Apple Store' => 34453,
+ 'Bank Millennium' => 37535,
+ 'Bank Pekao' => 37534,
+ 'Battlefield' => 37471,
+ 'BGŻ BNP Paribas' => 37530,
+ 'Binance' => 36946,
+ 'Blizzard Battle.net' => 36783,
+ 'Call of Duty' => 38923,
+ 'Chomikuj' => 33803,
+ 'Clash Royale' => 38950,
+ 'Cloudflare' => 38624,
+ 'Counter-Strike' => 36648,
+ 'Cyfrowy Polsat' => 33866,
+ 'Dead By Daylight' => 36599,
+ 'Deezer' => 33837,
+ 'Destiny' => 38945,
+ 'Deutsche bank Polska' => 36176,
+ 'Discord' => 36761,
+ 'Dota 2' => 36447,
+ 'Dropbox' => 33796,
+ 'EA' => 36448,
+ 'East&West' => 35641,
+ 'eBay' => 38579,
+ 'Elite: Dangerous' => 37778,
+ 'Epic Games Store' => 39022,
+ 'Escape from Tarkov' => 39060,
+ 'Eurobank' => 37008,
+ 'Facebook' => 33634,
+ 'Facebook Messenger' => 33635,
+ 'Facetime' => 34591,
+ 'Fifa' => 37086,
+ 'For Honor' => 37305,
+ 'Fortnite' => 36693,
+ 'Get in Bank' => 37532,
+ 'GG (Gadu Gadu)' => 33809,
+ 'Ghost Recon' => 38997,
+ 'GitHub' => 38466,
+ 'Gmail' => 33636,
+ 'Google' => 33637,
+ 'Google Hangouts' => 33638,
+ 'Google Play' => 33639,
+ 'Gran Turismo' => 36916,
+ 'Grindr' => 38741,
+ 'GTA 5' => 36848,
+ 'Guild Wars 2' => 36467,
+ 'Gumtree' => 33805,
+ 'HBO' => 36355,
+ 'Heyah' => 33812,
+ 'Home.pl' => 37537,
+ 'iCloud' => 33640,
+ 'Idea Bank' => 37533,
+ 'iMessage' => 33641,
+ 'Inea' => 34415,
+ 'ING Bank' => 33807,
+ 'Instagram' => 33642,
+ 'iTunes' => 33643,
+ 'Kraken' => 36983,
+ 'League of Legends' => 36629,
+ 'LinkedIn' => 33806,
+ 'Mbank' => 33800,
+ 'Multimedia Polska' => 33879,
+ 'Nazwa' => 37320,
+ 'Nest Bank' => 37529,
+ 'Netflix' => 35728,
+ 'Netia' => 33815,
+ 'NK.pl (Nasza-klasa)' => 33808,
+ 'O2' => 33801,
+ 'Office 365' => 35125,
+ 'OLX' => 33802,
+ 'OneDrive' => 36868,
+ 'Orange' => 33810,
+ 'Origin' => 36899,
+ 'Outlook' => 33644,
+ 'Overwatch' => 36388,
+ 'Path of Exile' => 37728,
+ 'PKO Bank Polski' => 36044,
+ 'Play' => 33813,
+ 'Player Unknown\'s Battlegrounds' => 36580,
+ 'Playstation Network' => 33645,
+ 'Plus' => 33814,
+ 'Pokémon Go' => 35752,
+ 'Rainbow Six' => 36394,
+ 'Reddit' => 37485,
+ 'Roblox' => 37400,
+ 'Rocket League' => 36667,
+ 'Santander' => 37531,
+ 'Sea of Thieves' => 37120,
+ 'Skype' => 33793,
+ 'Slack' => 37338,
+ 'Snapchat' => 33797,
+ 'Spotify' => 33836,
+ 'Steam' => 34279,
+ 'T-Mobile' => 33811,
+ 'Teamviewer' => 35694,
+ 'Telegram' => 35970,
+ 'The elder scrolls online' => 37328,
+ 'Tinder' => 36547,
+ 'Tumblr' => 37285,
+ 'Twitch' => 36450,
+ 'Twitter' => 33646,
+ 'UPC' => 33816,
+ 'Uplay PC' => 35612,
+ 'Vectra' => 33817,
+ 'Viber' => 33794,
+ 'Warframe' => 36493,
+ 'Whatsapp' => 33792,
+ 'Wikipedia' => 33647,
+ 'World of Tanks' => 36029,
+ 'World of Warcraft' => 37446,
+ 'World of Warships' => 38008,
+ 'Xbox Live' => 33648,
+ 'Yahoo Mail' => 38887,
+ 'Youtube' => 33649,
+ 'Z1 Battle Royale' => 37267,
+ ),
+ 'Norge' => array(
+ 'Altibox' => 36318,
+ 'Anthem' => 38206,
+ 'Apex Legends' => 38120,
+ 'App Store' => 38100,
+ 'Battlefield' => 37098,
+ 'Binance' => 36928,
+ 'Blizzard Battle.net' => 36309,
+ 'Call of Duty' => 36708,
+ 'Coinbase' => 36799,
+ 'Counter-strike' => 36647,
+ 'Crunchyroll' => 36720,
+ 'Danske Bank' => 36321,
+ 'Dead By Daylight' => 37426,
+ 'Destiny' => 36592,
+ 'Discord' => 36762,
+ 'Dota 2' => 36442,
+ 'EA' => 36310,
+ 'Epic Games Store' => 39028,
+ 'Facebook' => 36238,
+ 'Facebook Messenger' => 36269,
+ 'Fifa' => 36908,
+ 'Fortnite' => 36687,
+ 'Get' => 36319,
+ 'Ghost Recon' => 39000,
+ 'Gmail' => 36255,
+ 'Google' => 36256,
+ 'Google Drive' => 36760,
+ 'Google Play' => 38528,
+ 'GTA 5' => 36847,
+ 'Guild Wars 2' => 36470,
+ 'HBO Nordic' => 36316,
+ 'iCloud' => 38844,
+ 'Ikano Bank' => 36577,
+ 'Instagram' => 36443,
+ 'Kraken' => 36853,
+ 'League of Legends' => 38630,
+ 'Minecraft' => 37280,
+ 'Netflix' => 36257,
+ 'NexGenTel' => 36320,
+ 'Nordea' => 36325,
+ 'Norges Bank' => 36324,
+ 'Office 365' => 36311,
+ 'OneDrive' => 36865,
+ 'Origin' => 36893,
+ 'Outlook' => 36258,
+ 'Overwatch' => 36259,
+ 'Path of Exile' => 37727,
+ 'Playerunknown\'s Battlegrounds' => 36338,
+ 'Playstation Network' => 36260,
+ 'Pokémon Go' => 36261,
+ 'Rainbow Six' => 36262,
+ 'Realm Royale' => 37316,
+ 'Red Dead Redemption' => 38283,
+ 'Reddit' => 36825,
+ 'Roblox' => 38919,
+ 'Rocket League' => 36312,
+ 'Sea of Thieves' => 37116,
+ 'Skype' => 36263,
+ 'Snapchat' => 36264,
+ 'Sparebanken 1' => 36323,
+ 'Spotify' => 36796,
+ 'Steam' => 36313,
+ 'Strava' => 38730,
+ 'Tele2' => 36317,
+ 'Telegram' => 37183,
+ 'Telenor' => 36288,
+ 'The elder scrolls online' => 37324,
+ 'Tinder' => 36314,
+ 'Twitch' => 36444,
+ 'Twitter' => 37268,
+ 'Uplay PC' => 36265,
+ 'Viaplay' => 37293,
+ 'Warframe' => 37129,
+ 'Whatsapp' => 36266,
+ 'Wikipedia' => 38872,
+ 'World of Warcraft' => 37447,
+ 'Xbox Live' => 36315,
+ 'Yahoo' => 36268,
+ 'Yahoo Mail' => 38890,
+ 'Youtube' => 36267,
+ 'Z1 Battle Royale' => 37262,
+ ),
+ 'México' => array(
+ 'Amazon' => 33292,
+ 'Amazon Prime Video' => 38752,
+ 'Anthem' => 38192,
+ 'Apex Legends' => 38139,
+ 'App Store' => 37732,
+ 'Apple Store' => 34466,
+ 'AT&T' => 35861,
+ 'Axtel' => 34439,
+ 'Banamex' => 33322,
+ 'Banco Santander' => 36772,
+ 'Banorte' => 33326,
+ 'Battlefield' => 38445,
+ 'BBVA Bancomer' => 33321,
+ 'Binance' => 37019,
+ 'Blizzard Battle.net' => 36106,
+ 'Cablecom' => 34035,
+ 'Cablemás' => 34438,
+ 'Call of Duty' => 35540,
+ 'Clash of Clans' => 37099,
+ 'Crunchyroll' => 37139,
+ 'Dead By Daylight' => 37432,
+ 'Deezer' => 33397,
+ 'Destiny' => 38966,
+ 'Discord' => 38606,
+ 'Dropbox' => 33294,
+ 'EA' => 36609,
+ 'eBay' => 33295,
+ 'Facebook' => 33296,
+ 'Facebook Messenger' => 33297,
+ 'Facetime' => 34594,
+ 'Fifa' => 38307,
+ 'Fortnite' => 36842,
+ 'Gears of War' => 38893,
+ 'Gmail' => 33298,
+ 'Go Daddy' => 36620,
+ 'Google' => 33299,
+ 'Google Drive' => 38260,
+ 'Google Hangouts' => 33300,
+ 'Google Play' => 33301,
+ 'Gran Turismo' => 36951,
+ 'Grindr' => 38740,
+ 'GTA 5' => 38275,
+ 'HBO' => 36351,
+ 'iCloud' => 33302,
+ 'iMessage' => 33303,
+ 'Instagram' => 33304,
+ 'iTunes' => 33305,
+ 'Izzi' => 37685,
+ 'League of Legends' => 39019,
+ 'Line' => 33395,
+ 'LinkedIn' => 33306,
+ 'Megacable' => 34437,
+ 'Mercado Libre' => 33320,
+ 'Microsoft Azure' => 37466,
+ 'Minecraft' => 38737,
+ 'Movistar' => 33307,
+ 'Netflix' => 33325,
+ 'Origin' => 38103,
+ 'Outlook' => 33308,
+ 'Overwatch' => 36483,
+ 'Paypal' => 33309,
+ 'Player Unknown\'s Battlegrounds' => 36562,
+ 'Playstation Network' => 33310,
+ 'Pokémon Go' => 36360,
+ 'Rainbow Six' => 36146,
+ 'Reddit' => 37482,
+ 'Roblox' => 38917,
+ 'Salesforce' => 38496,
+ 'Scotiabank' => 37686,
+ 'Segunda Mano' => 33327,
+ 'SKY México' => 33328,
+ 'Skype' => 33311,
+ 'Snapchat' => 34288,
+ 'SPEI' => 37689,
+ 'Spotify' => 33398,
+ 'Steam' => 34281,
+ 'Tango' => 33745,
+ 'Teamviewer' => 35689,
+ 'Telcel' => 33319,
+ 'Telegram' => 35852,
+ 'Telmex' => 33324,
+ 'Telnor' => 34440,
+ 'Tinder' => 37165,
+ 'Totalplay' => 37687,
+ 'Tweakbox' => 38903,
+ 'Twitch' => 36546,
+ 'Twitter' => 33312,
+ 'Unefon' => 37688,
+ 'WeChat' => 33399,
+ 'Whatsapp' => 33313,
+ 'Wikipedia' => 33314,
+ 'World of Warcraft' => 38880,
+ 'Xbox Live' => 33315,
+ 'Yahoo' => 33316,
+ 'Yahoo Mail' => 33317,
+ 'Yahoo Messenger' => 33318,
+ 'Youtube' => 33361,
+ 'Zello' => 33388,
+ ),
+ '日本' => array(
+ 'Amazon' => 33464,
+ 'Amazon Web Services' => 34094,
+ 'Amazon インスタント・ビデオ' => 34496,
+ 'Apex Legends' => 38177,
+ 'App Store' => 35581,
+ 'Apple Store' => 34467,
+ 'ASAHI ネット' => 33859,
+ 'Au' => 33465,
+ 'Biglobe' => 33479,
+ 'Blizzard Battle.net' => 36672,
+ 'bmobile' => 33466,
+ 'Call of Duty' => 39053,
+ 'Dazn' => 36511,
+ 'Discord' => 38613,
+ 'Disney Mobile' => 33467,
+ 'DMM' => 35818,
+ 'Dropbox' => 33441,
+ 'EA' => 37080,
+ 'eBay' => 33442,
+ 'EO Net' => 33863,
+ 'Facebook' => 33443,
+ 'Facebook Messenger' => 33444,
+ 'Facetime' => 34593,
+ 'FC2' => 34510,
+ 'Fortnite' => 37162,
+ 'Freetel' => 35620,
+ 'Ghost Recon' => 38993,
+ 'Github' => 37375,
+ 'Gmail' => 33445,
+ 'Google' => 33446,
+ 'Google Hangouts' => 33447,
+ 'Google Play' => 33448,
+ 'Hulu' => 33480,
+ 'iCloud' => 33449,
+ 'IIJ' => 34511,
+ 'iMessage' => 33450,
+ 'Instagram' => 33451,
+ 'iTunes' => 33452,
+ 'Jcom' => 33478,
+ 'League of Legends' => 38899,
+ 'Line' => 33453,
+ 'LinkedIn' => 33454,
+ 'Livedoor' => 33472,
+ 'Microsoft Azure' => 36110,
+ 'Netflix' => 36728,
+ 'Nifty' => 33473,
+ 'Nintendo Network' => 35521,
+ 'NTT Docomo' => 33474,
+ 'NTT東日本' => 33475,
+ 'NTT西日本' => 33476,
+ 'OCN' => 33564,
+ 'Office 365' => 35928,
+ 'OneDrive' => 36496,
+ 'Outlook' => 33455,
+ 'Paypal' => 33456,
+ 'Player Unknown\'s Battlegrounds' => 36616,
+ 'Playstation Network' => 33457,
+ 'Rakuten' => 34513,
+ 'Reddit' => 37478,
+ 'Skype' => 33458,
+ 'Slack' => 37358,
+ 'Snapchat' => 38511,
+ 'So-net' => 33862,
+ 'Steam' => 38649,
+ 'Telegram' => 37227,
+ 'Tinder' => 37916,
+ 'Twitter' => 33459,
+ 'UQ Wimax' => 33482,
+ 'Whatsapp' => 38255,
+ 'Xbox Live' => 33471,
+ 'Yahoo' => 33460,
+ 'Yahoo BB' => 33860,
+ 'Yahoo Mail' => 33461,
+ 'Yammer' => 35560,
+ 'Youtube' => 33462,
+ 'じぶん銀行' => 33500,
+ 'ぷらら' => 33861,
+ 'みずほ銀行' => 33493,
+ 'りそな銀行' => 33496,
+ 'アメーバブログ' => 34514,
+ 'カカオトーク' => 33469,
+ 'ジャパンネット銀行' => 33497,
+ 'スカパー' => 33477,
+ 'スポナビLive' => 36516,
+ 'ソニー銀行' => 33498,
+ 'ソフトバンク' => 33470,
+ 'ポケモン go' => 35746,
+ 'ワイモバイル' => 36503,
+ '三井住友銀行' => 33495,
+ '三菱東京UFJ銀行' => 33494,
+ '埼玉りそな銀行' => 36532,
+ '楽天銀行' => 33499,
+ '近畿大阪銀行' => 36531,
+ ),
+ 'Pilipinas' => array(
+ 'Anthem' => 38193,
+ 'Apex Legends' => 38158,
+ 'Battlefield' => 37925,
+ 'Blizzard Battle.net' => 37834,
+ 'Converge' => 38714,
+ 'Counter-strike' => 38241,
+ 'Destiny' => 38987,
+ 'Discord' => 38453,
+ 'Dota 2' => 37835,
+ 'EA' => 37931,
+ 'Facebook' => 37836,
+ 'Facebook Messenger' => 37837,
+ 'Fortnite' => 37930,
+ 'Globe' => 37941,
+ 'Gmail' => 38080,
+ 'Google' => 37838,
+ 'Google Drive' => 38259,
+ 'Google Hangouts' => 38365,
+ 'Google Play' => 38521,
+ 'GTA 5' => 38718,
+ 'iCloud' => 38853,
+ 'Instagram' => 37839,
+ 'League of Legends' => 38911,
+ 'Mobile legends' => 38175,
+ 'Netflix' => 37840,
+ 'Office 365' => 37936,
+ 'Origin' => 38397,
+ 'Outlook' => 37935,
+ 'Overwatch' => 37932,
+ 'Paypal' => 38463,
+ 'Player Unknown\'s Battlegrounds' => 37841,
+ 'Playstation Network' => 38736,
+ 'PLDT' => 37938,
+ 'Rainbow Six' => 37933,
+ 'Reddit' => 38089,
+ 'Roblox' => 37927,
+ 'Sky Cable' => 37942,
+ 'Skype' => 37929,
+ 'Smart' => 37940,
+ 'Spotify' => 38644,
+ 'Steam' => 37924,
+ 'Telegram' => 38019,
+ 'Tinder' => 37912,
+ 'TNT' => 37943,
+ 'Twitter' => 37928,
+ 'Warframe' => 37934,
+ 'Wattpad' => 38962,
+ 'Waze' => 38267,
+ 'Whatsapp' => 38254,
+ 'Yahoo' => 37926,
+ 'Yahoo Mail' => 38456,
+ 'Youtube' => 37842,
+ ),
+ 'Indonesia' => array(
+ 'Anthem' => 38194,
+ 'Apex Legends' => 38181,
+ 'Biznet' => 38975,
+ 'Blizzard Battle.net' => 37825,
+ 'Clash of Clans' => 37961,
+ 'Counter-strike' => 38410,
+ 'Discord' => 38084,
+ 'Dota 2' => 37826,
+ 'EA' => 38419,
+ 'Facebook' => 37827,
+ 'Fifa' => 38427,
+ 'First Media' => 38974,
+ 'Fortnite' => 38532,
+ 'Gmail' => 38250,
+ 'Google' => 37828,
+ 'Google Drive' => 38262,
+ 'Google Play' => 38518,
+ 'GTA 5' => 38700,
+ 'iCloud' => 38851,
+ 'Indosat Ooredoo' => 38978,
+ 'Instagram' => 37829,
+ 'Myrepublic' => 38972,
+ 'Netflix' => 37830,
+ 'Origin' => 38376,
+ 'Pinterest' => 37950,
+ 'Player Unknown\'s Battlegrounds' => 37831,
+ 'Playstation Network' => 38735,
+ 'Reddit' => 38498,
+ 'Roblox' => 38914,
+ 'Steam' => 38098,
+ 'Telegram' => 38020,
+ 'Telkom' => 38973,
+ 'Telkomsel' => 38976,
+ 'Tinder' => 37915,
+ 'Twitter' => 38160,
+ 'Uplay PC' => 37962,
+ 'Whatsapp' => 37832,
+ 'XL' => 38977,
+ 'Yahoo Mail' => 38889,
+ 'Youtube' => 37833,
+ ),
+ 'Pakistan' => array(
+ 'Apex Legends' => 38414,
+ 'App Store' => 38960,
+ 'Battlefield' => 38002,
+ 'Blizzard Battle.net' => 37992,
+ 'Call of Duty' => 38939,
+ 'Discord' => 37993,
+ 'Dota 2' => 38476,
+ 'EA' => 38418,
+ 'Facebook' => 37994,
+ 'Facebook Messenger' => 37995,
+ 'Fiberlink' => 38006,
+ 'Fifa' => 38425,
+ 'Fortnite' => 38252,
+ 'Google' => 37996,
+ 'iCloud' => 38715,
+ 'Instagram' => 37997,
+ 'Kik' => 38539,
+ 'Netflix' => 37998,
+ 'Pinterest' => 38679,
+ 'Player Unknown\'s Battlegrounds' => 37999,
+ 'Playstation Network' => 38571,
+ 'PTLC' => 38004,
+ 'Quora' => 38908,
+ 'Snapchat' => 38508,
+ 'Steam' => 38341,
+ 'Tinder' => 38000,
+ 'Tumblr' => 38546,
+ 'Twitter' => 38678,
+ 'Wateen' => 38007,
+ 'Wattpad' => 38544,
+ 'Whatsapp' => 38003,
+ 'Yahoo Mail' => 38882,
+ 'Youtube' => 38001,
+ 'Zong' => 38005,
+ ),
+ 'UAE' => array(
+ 'Apex Legends' => 38159,
+ 'beIN' => 39073,
+ 'Binance' => 37022,
+ 'Blizzard Battle.net' => 36214,
+ 'Botim' => 38393,
+ 'Call of Duty' => 38935,
+ 'Cloudflare' => 38642,
+ 'Counter-strike' => 38269,
+ 'Dead By Daylight' => 37437,
+ 'Discord' => 37773,
+ 'Dota 2' => 36423,
+ 'Du' => 36235,
+ 'EA' => 36883,
+ 'Etisalat' => 36234,
+ 'Facebook' => 36215,
+ 'Facebook Messenger' => 36233,
+ 'Fifa' => 38433,
+ 'For Honor' => 36216,
+ 'Fortnite' => 36996,
+ 'Gmail' => 36217,
+ 'Google' => 36218,
+ 'iCloud' => 38843,
+ 'Instagram' => 36420,
+ 'Netflix' => 36219,
+ 'Office 365' => 38041,
+ 'Origin' => 38422,
+ 'Outlook' => 36220,
+ 'Overwatch' => 36221,
+ 'Player Unknown\'s Battlegrounds' => 36618,
+ 'Playstation Network' => 36222,
+ 'Pokémon Go' => 36223,
+ 'Rainbow Six' => 36224,
+ 'Reddit' => 38499,
+ 'Roblox' => 37222,
+ 'Rocket League' => 36231,
+ 'Skype' => 36225,
+ 'Snapchat' => 36226,
+ 'Steam' => 38340,
+ 'Telegram' => 37185,
+ 'Tinder' => 36227,
+ 'Twitter' => 38677,
+ 'Uplay PC' => 36228,
+ 'Whatsapp' => 36229,
+ 'Wikipedia' => 38878,
+ 'Xbox Live' => 38404,
+ 'Yahoo' => 36232,
+ 'Yahoo Mail' => 38888,
+ 'Youtube' => 36230,
+ 'ZoHo' => 37553,
+ ),
+ 'Malaysia' => array(
+ 'Apex Legends' => 38179,
+ 'Blizzard Battle.net' => 37891,
+ 'Counter-strike' => 38409,
+ 'Destiny' => 38985,
+ 'Discord' => 37976,
+ 'Dota 2' => 38017,
+ 'EA' => 38420,
+ 'Facebook' => 37892,
+ 'Facebook Messenger' => 37893,
+ 'Fifa' => 38429,
+ 'Gmail' => 38251,
+ 'Google' => 37894,
+ 'Google Drive' => 38263,
+ 'Google Play' => 38529,
+ 'GTA 5' => 38488,
+ 'iCloud' => 38850,
+ 'Instagram' => 37895,
+ 'League of Legends' => 38910,
+ 'Line' => 38386,
+ 'LinkedIn' => 38150,
+ 'Maxis' => 37964,
+ 'Netflix' => 37896,
+ 'Origin' => 38395,
+ 'Overwatch' => 38895,
+ 'Paypal' => 38461,
+ 'Player Unknown\'s Battlegrounds' => 37897,
+ 'Playstation Network' => 38570,
+ 'Reddit' => 38363,
+ 'Roblox' => 38912,
+ 'Snapchat' => 38548,
+ 'Steam' => 38081,
+ 'TIME' => 37965,
+ 'Tinder' => 37917,
+ 'Twitter' => 38481,
+ 'Unifi' => 37963,
+ 'Uplay PC' => 38896,
+ 'Waze' => 38268,
+ 'Whatsapp' => 38028,
+ 'Yahoo Mail' => 38891,
+ 'Youtube' => 37898,
+ ),
+ 'Perú' => array(
+ 'Apex Legends' => 39015,
+ 'Bitel' => 37982,
+ 'Claro' => 37981,
+ 'Crunchyroll' => 38550,
+ 'Dota 2' => 38353,
+ 'EA' => 38415,
+ 'Econocable' => 37983,
+ 'Entel' => 37980,
+ 'Facebook' => 37791,
+ 'Facebook Messenger' => 38258,
+ 'Fortnite' => 37792,
+ 'Gmail' => 37944,
+ 'Google' => 37945,
+ 'HBO' => 38369,
+ 'iCloud' => 38855,
+ 'Instagram' => 37793,
+ 'Movistar' => 37794,
+ 'Netflix' => 38594,
+ 'Origin' => 38423,
+ 'Outlook' => 38581,
+ 'Playstation Network' => 38568,
+ 'Spotify' => 38580,
+ 'Steam' => 38099,
+ 'Telegram' => 38483,
+ 'Tinder' => 37909,
+ 'Twitter' => 38105,
+ 'Whatsapp' => 37795,
+ 'Youtube' => 37796,
+ ),
+ 'Argentina' => array(
+ 'Apex Legends' => 38129,
+ 'Arnet' => 37969,
+ 'Banco Galicia' => 36132,
+ 'Banco Nación' => 36131,
+ 'Banco Provincia' => 36133,
+ 'Banco Santander Río ' => 36130,
+ 'BBVA Francés' => 36134,
+ 'Binance' => 37020,
+ 'Blizzard Battle.net' => 36104,
+ 'Call of Duty' => 36743,
+ 'Claro' => 36100,
+ 'Clash of Clans' => 36128,
+ 'Correo Argentino' => 36999,
+ 'Counter-Strike' => 38247,
+ 'Crunchyroll' => 38091,
+ 'Dead By Daylight' => 37431,
+ 'Destiny' => 38965,
+ 'Discord' => 38614,
+ 'Dota 2' => 37187,
+ 'EA' => 36885,
+ 'Facebook' => 36072,
+ 'Facebook Messenger' => 36073,
+ 'Fibertel' => 36635,
+ 'Fifa' => 38435,
+ 'Flow' => 38309,
+ 'Fortnite' => 37017,
+ 'Free Fire' => 38806,
+ 'Gigared' => 38215,
+ 'Gmail' => 37716,
+ 'Google' => 36074,
+ 'Google Play' => 38520,
+ 'GTA 5' => 38276,
+ 'HBO' => 36352,
+ 'ICBC' => 38646,
+ 'iCloud' => 38858,
+ 'Instagram' => 36075,
+ 'Mercado Libre' => 36076,
+ 'Microsoft Azure' => 37467,
+ 'Movistar' => 36077,
+ 'Netflix' => 36078,
+ 'Nextel' => 36103,
+ 'OLX' => 37045,
+ 'Origin' => 36902,
+ 'Outlook' => 36079,
+ 'Overwatch' => 38774,
+ 'Path of Exile' => 37771,
+ 'Personal' => 37970,
+ 'Player Unknown\'s Battlegrounds' => 36563,
+ 'Playstation Network' => 36080,
+ 'Pokémon Go' => 36294,
+ 'Rainbow Six' => 36144,
+ 'Reddit' => 37483,
+ 'Roblox' => 38929,
+ 'Skype' => 36081,
+ 'Snapchat' => 36082,
+ 'Spotify' => 36107,
+ 'Steam' => 36129,
+ 'Teamviewer' => 36142,
+ 'Telecentro' => 36810,
+ 'Telecom' => 36097,
+ 'Telefónica' => 36099,
+ 'Telegram' => 38485,
+ 'Telered' => 37971,
+ 'Tinder' => 37169,
+ 'Tuenti' => 38628,
+ 'Twitch' => 36544,
+ 'Twitter' => 36109,
+ 'Uplay PC' => 36143,
+ 'Waze' => 37470,
+ 'Whatsapp' => 36083,
+ 'Wikipedia' => 37352,
+ 'World of Warcraft' => 38778,
+ 'Xbox Live' => 37443,
+ 'Yahoo Mail' => 36084,
+ 'Youtube' => 36085,
+ ),
+ 'Slovensko' => array(
+ 'Apex Legends' => 38131,
+ 'Blizzard Battle.net' => 37875,
+ 'Counter-strike' => 38243,
+ 'Discord' => 38612,
+ 'Dota 2' => 38480,
+ 'EA' => 38417,
+ 'Facebook' => 37876,
+ 'Facebook Messenger' => 37877,
+ 'Fifa' => 38426,
+ 'Fortnite' => 38807,
+ 'Google' => 37878,
+ 'GTA 5' => 38279,
+ 'HBO Go' => 38381,
+ 'iCloud' => 38848,
+ 'Instagram' => 37879,
+ 'Netflix' => 37880,
+ 'Origin' => 38374,
+ 'Player Unknown\'s Battlegrounds' => 37881,
+ 'Playstation Network' => 38572,
+ 'Reddit' => 38809,
+ 'Snapchat' => 38513,
+ 'Steam' => 38230,
+ 'Twitter' => 38669,
+ 'Whatsapp' => 38371,
+ 'Wikipedia' => 38877,
+ 'Xbox Live' => 38088,
+ 'Yahoo Mail' => 38881,
+ 'Youtube' => 37882,
+ ),
+ 'Ελλάς' => array(
+ 'Apex Legends' => 38132,
+ 'Bet365' => 38811,
+ 'Blizzard Battle.net' => 37843,
+ 'Clash Royale' => 38949,
+ 'Counter-strike' => 38235,
+ 'Destiny' => 38980,
+ 'Discord' => 38607,
+ 'Dota 2' => 38352,
+ 'EA' => 38416,
+ 'eBay' => 38578,
+ 'Facebook' => 37844,
+ 'Facebook Messenger' => 37845,
+ 'Fifa' => 38434,
+ 'Fortnite' => 38087,
+ 'Gmail' => 38079,
+ 'Google' => 37846,
+ 'Google Play' => 38527,
+ 'GTA 5' => 38701,
+ 'iCloud' => 38846,
+ 'Instagram' => 37847,
+ 'League of Legends' => 38618,
+ 'Netflix' => 37848,
+ 'Office 365' => 38076,
+ 'Origin' => 38375,
+ 'Paypal' => 38462,
+ 'Player Unknown\'s Battlegrounds' => 37849,
+ 'Playstation Network' => 38575,
+ 'Pokémon Go' => 38639,
+ 'Reddit' => 38516,
+ 'Snapchat' => 38505,
+ 'Steam' => 38231,
+ 'Twitch' => 38582,
+ 'Twitter' => 38676,
+ 'Viber' => 38588,
+ 'Whatsapp' => 38373,
+ 'Yahoo Mail' => 38892,
+ 'Youtube' => 37850,
+ 'Βικιπαίδεια' => 38873,
+ ),
+ 'Hrvatska' => array(
+ 'Apex Legends' => 38135,
+ 'Battlefield' => 38442,
+ 'Blizzard Battle.net' => 37859,
+ 'Clash Royale' => 38356,
+ 'Counter-strike' => 38244,
+ 'Destiny' => 39011,
+ 'Discord' => 38610,
+ 'Dota 2' => 38351,
+ 'EA' => 38036,
+ 'Facebook' => 37860,
+ 'Facebook Messenger' => 37861,
+ 'Fifa' => 38438,
+ 'Fortnite' => 38069,
+ 'Google' => 37862,
+ 'GTA 5' => 38278,
+ 'HBO Go' => 38384,
+ 'iCloud' => 38847,
+ 'Instagram' => 37863,
+ 'Netflix' => 37864,
+ 'Office 365' => 38075,
+ 'Origin' => 38149,
+ 'Player Unknown\'s Battlegrounds' => 37865,
+ 'Playstation Network' => 38574,
+ 'Reddit' => 38090,
+ 'Snapchat' => 38509,
+ 'Steam' => 38229,
+ 'Tinder' => 37920,
+ 'Twitter' => 38672,
+ 'Whatsapp' => 38026,
+ 'Wikipedia' => 38874,
+ 'Yahoo Mail' => 38884,
+ 'Youtube' => 37866,
+ ),
+ 'Česko' => array(
+ 'Apex Legends' => 38136,
+ 'Battlefield' => 38446,
+ 'Blizzard Battle.net' => 37851,
+ 'Counter-strike' => 38236,
+ 'Discord' => 38452,
+ 'Dota 2' => 38221,
+ 'EA' => 38037,
+ 'Facebook' => 37852,
+ 'Facebook Messenger' => 37853,
+ 'Fifa' => 38430,
+ 'Fortnite' => 38086,
+ 'Gmail' => 38515,
+ 'Google' => 37854,
+ 'Google Play' => 38523,
+ 'GTA 5' => 38304,
+ 'HBO Go' => 38380,
+ 'iCloud' => 38845,
+ 'Instagram' => 37855,
+ 'Netflix' => 37856,
+ 'Office 365' => 38042,
+ 'Origin' => 38043,
+ 'Player Unknown\'s Battlegrounds' => 37857,
+ 'Playstation Network' => 38573,
+ 'Reddit' => 38062,
+ 'Snapchat' => 38512,
+ 'Steam' => 38082,
+ 'Tinder' => 37914,
+ 'Twitch' => 38530,
+ 'Twitter' => 38675,
+ 'Uplay PC' => 38638,
+ 'Whatsapp' => 38025,
+ 'Xbox Live' => 38072,
+ 'Youtube' => 37858,
+ ),
+ 'Chile' => array(
+ 'Apex Legends' => 38137,
+ 'Banco Estado' => 37682,
+ 'Banco Santander' => 37351,
+ 'Blizzard Battle.net' => 38104,
+ 'Call of Duty' => 38938,
+ 'Claro' => 36290,
+ 'Clash of Clans' => 37304,
+ 'Correos' => 37025,
+ 'Counter-Strike' => 38246,
+ 'Crunchyroll' => 38093,
+ 'Dead By Daylight' => 37436,
+ 'Discord' => 37758,
+ 'Dota 2' => 38477,
+ 'EA' => 36884,
+ 'Entel' => 37680,
+ 'Facebook' => 36239,
+ 'Facebook Messenger' => 36285,
+ 'Falabella' => 37681,
+ 'Fifa' => 38432,
+ 'Fortnite' => 36997,
+ 'Gmail' => 36499,
+ 'Google' => 36284,
+ 'Google Drive' => 38560,
+ 'GTA 5' => 38305,
+ 'Gtd Manquehue' => 37683,
+ 'HBO' => 36353,
+ 'iCloud' => 38854,
+ 'Instagram' => 36283,
+ 'Itaú' => 38473,
+ 'LinkedIn' => 38625,
+ 'Movistar' => 36289,
+ 'Mundo Pacifico' => 37684,
+ 'Netflix' => 36282,
+ 'Office 365' => 38077,
+ 'Origin' => 38102,
+ 'Outlook' => 36281,
+ 'Player Unknown\'s Battlegrounds' => 36564,
+ 'Playstation Network' => 36280,
+ 'Pokémon Go' => 36293,
+ 'Rainbow Six' => 36270,
+ 'Reddit' => 37484,
+ 'Roblox' => 38930,
+ 'SII' => 37679,
+ 'Skype' => 36279,
+ 'Snapchat' => 36278,
+ 'Spotify' => 36274,
+ 'Steam' => 36272,
+ 'Teamviewer' => 37068,
+ 'Telegram' => 38170,
+ 'Telsur' => 36292,
+ 'Tinder' => 37907,
+ 'Twitch' => 36541,
+ 'Twitter' => 36273,
+ 'Uplay PC' => 36271,
+ 'VTR' => 36291,
+ 'Warframe' => 37123,
+ 'Whatsapp' => 36277,
+ 'Wom' => 38308,
+ 'Xbox Live' => 37024,
+ 'Yahoo Mail' => 36276,
+ 'Youtube' => 36275,
+ ),
+ 'Colombia' => array(
+ 'Apex Legends' => 38140,
+ 'BBVA' => 37781,
+ 'Blizzard Battle.net' => 38148,
+ 'Call of Duty' => 38937,
+ 'Claro' => 37788,
+ 'Directv' => 37968,
+ 'Discord' => 38552,
+ 'EA' => 38282,
+ 'ETB' => 37967,
+ 'Facebook' => 37782,
+ 'Facebook Messenger' => 38257,
+ 'Fifa' => 38431,
+ 'Fortnite' => 37783,
+ 'Free Fire' => 38805,
+ 'Gmail' => 37779,
+ 'Google' => 37780,
+ 'Google Drive' => 39067,
+ 'GTA 5' => 38277,
+ 'HBO' => 38370,
+ 'iCloud' => 38857,
+ 'Instagram' => 37784,
+ 'Movistar' => 37789,
+ 'Netflix' => 37820,
+ 'Origin' => 38424,
+ 'Outlook' => 38464,
+ 'Player Unknown\'s Battlegrounds' => 37785,
+ 'Playstation Network' => 38391,
+ 'Snapchat' => 38506,
+ 'Spotify' => 38168,
+ 'Steam' => 38933,
+ 'Teamviewer' => 38460,
+ 'Telegram' => 38484,
+ 'Tigo' => 37966,
+ 'Tinder' => 37908,
+ 'Twitter' => 38169,
+ 'Waze' => 39070,
+ 'Whatsapp' => 37786,
+ 'Xbox Live' => 38071,
+ 'Yahoo Mail' => 38924,
+ 'Youtube' => 37787,
+ ),
+ 'România' => array(
+ 'Apex Legends' => 38142,
+ 'Battlefield' => 38441,
+ 'Blizzard Battle.net' => 37867,
+ 'Brawl Stars' => 38817,
+ 'Call of Duty' => 38934,
+ 'Counter-strike' => 38237,
+ 'Destiny' => 38988,
+ 'Digi' => 38971,
+ 'Discord' => 37953,
+ 'Dota 2' => 38222,
+ 'EA' => 38039,
+ 'Facebook' => 37868,
+ 'Facebook Messenger' => 37869,
+ 'Fifa' => 38046,
+ 'Fortnite' => 38070,
+ 'Gmail' => 38549,
+ 'Google' => 37870,
+ 'Google Play' => 38524,
+ 'GTA 5' => 38281,
+ 'HBO Go' => 38383,
+ 'iCloud' => 38849,
+ 'Instagram' => 37871,
+ 'Netflix' => 37872,
+ 'Orange' => 38970,
+ 'Origin' => 38045,
+ 'Player Unknown\'s Battlegrounds' => 37873,
+ 'Playstation Network' => 38407,
+ 'Reddit' => 38063,
+ 'Roblox' => 38918,
+ 'Snapchat' => 38510,
+ 'Steam' => 38083,
+ 'Telekom' => 38931,
+ 'Tinder' => 37913,
+ 'Twitter' => 38674,
+ 'UPC' => 38968,
+ 'Uplay PC' => 38637,
+ 'Vodafone' => 38967,
+ 'Whatsapp' => 38027,
+ 'Wikipedia' => 38875,
+ 'Xbox Live' => 38073,
+ 'Yahoo Mail' => 38455,
+ 'Youtube' => 37874,
+ ),
+ 'Magyarország' => array(
+ 'Apex Legends' => 38143,
+ 'Battlefield' => 38450,
+ 'Blizzard Battle.net' => 37883,
+ 'Call of Duty' => 39004,
+ 'Counter-strike' => 38242,
+ 'Destiny' => 38979,
+ 'Discord' => 38454,
+ 'Dota 2' => 38475,
+ 'EA' => 38038,
+ 'Escape from Tarkov' => 39055,
+ 'Facebook' => 37884,
+ 'Facebook Messenger' => 37885,
+ 'Fifa' => 38437,
+ 'Fortnite' => 38808,
+ 'Ghost Recon' => 38991,
+ 'Gmail' => 38514,
+ 'Google' => 37886,
+ 'GTA 5' => 38280,
+ 'HBO Go' => 38382,
+ 'iCloud' => 38852,
+ 'Instagram' => 37887,
+ 'Mastercard' => 38592,
+ 'Netflix' => 37888,
+ 'Office 365' => 38040,
+ 'Origin' => 38044,
+ 'Outlook' => 38078,
+ 'Pinterest' => 37954,
+ 'Player Unknown\'s Battlegrounds' => 37889,
+ 'Playstation Network' => 38408,
+ 'Rainbow Six' => 38486,
+ 'Reddit' => 38065,
+ 'Snapchat' => 38507,
+ 'Steam' => 38232,
+ 'Tinder' => 37910,
+ 'Twitch' => 39016,
+ 'Twitter' => 38673,
+ 'Uplay PC' => 38354,
+ 'Whatsapp' => 38372,
+ 'Wikipedia' => 38876,
+ 'Xbox Live' => 38074,
+ 'Yahoo Mail' => 38886,
+ 'Youtube' => 37890,
+ ),
+ 'Ecuador' => array(
+ 'Call of Duty' => 38936,
+ 'Claro' => 37985,
+ 'CNT' => 37990,
+ 'EA' => 38421,
+ 'Facebook' => 37797,
+ 'Facebook Messenger' => 38256,
+ 'Fortnite' => 37798,
+ 'HBO' => 38368,
+ 'iCloud' => 38856,
+ 'Instagram' => 37799,
+ 'iPlanet' => 37986,
+ 'Movistar' => 37984,
+ 'Nedetel' => 37987,
+ 'Netflix' => 37819,
+ 'Netlife' => 37991,
+ 'Playstation Network' => 38577,
+ 'Puntonet' => 37988,
+ 'Steam' => 38932,
+ 'Telegram' => 38482,
+ 'TVCable' => 37989,
+ 'Twitter' => 38670,
+ 'Whatsapp' => 37800,
+ 'Youtube' => 37801,
+ ),
+ )
+ )
+ ),
+ );
+
+ const API_TOKEN = 'YW5kcm9pZF9hcGlfdXNlcl92MTpxTkRyenZSczY1bW1ESlk0ZVNIWmtobFY=';
+
+ public function collectData(){
+
+ if($this->queriedContext == 'All Websites') {
+ $html = getSimpleHTMLDOM($this->getURI() . '/archive/')
+ or returnClientError('Impossible to query website !.');
+
+ $table = $html->find('table.table-striped', 0);
+
+ $maxCount = 10;
+ foreach ($table->find('tr') as $downEvent) {
+ $downLink = $downEvent->find('td', 1)->find('a', 1);
+ $item = $this->collectArticleData($downLink->getAttribute('href'));
+ $this->items[] = $item;
+ if($maxCount == 0) break;
+ $maxCount -= 1;
+ }
+ } else {
+ $this->items = $this->collectCompanyEvents($this->getInput('website'));
+ }
+ }
+
+ protected function collectArticleData($link) {
+
+ preg_match('/\/([0-9]{3,})/', $link, $matches);
+ $eventId = $matches[1];
+
+ $header = array(
+ 'Authorization: Basic ' . self::API_TOKEN
+ );
+
+ $article = getContents('https://downdetectorapi.com/v1/events/' . $eventId, $header)
+ or returnServerError('Could not request DownDetector API.');
+ $article_json = json_decode($article);
+
+ $item = array();
+ $item['uri'] = $this->getURI() . $link;
+ $item['id'] = $article_json->id;
+ $item['title'] = $article_json->title;
+ $item['content'] = $article_json->body;
+ $item['timestamp'] = (new DateTime($article_json->started_at))->getTimestamp();
+ return $item;
+
+ }
+
+ protected function collectCompanyEvents($companyId) {
+
+ $header = array(
+ 'Authorization: Basic ' . self::API_TOKEN
+ );
+
+ $events = getContents('https://downdetectorapi.com/v1/companies/' . $companyId . '/events/', $header)
+ or returnServerError('Could not request DownDetector API.');
+ $events_json = json_decode($events);
+
+ $items = array();
+
+ foreach($events_json as $event) {
+ $item = array();
+ $item['id'] = $event->id;
+ $item['title'] = $event->title;
+ $item['content'] = $event->body;
+ $item['timestamp'] = (new DateTime($event->started_at))->getTimestamp();
+ $items[] = $item;
+ }
+
+ return $items;
+
+ }
+
+ public function getURI() {
+ if($this->getInput('country') !== null) {
+ return $this->getInput('country');
+ } else {
+ return self::URI;
+ }
+ }
+}
diff --git a/bridges/DribbbleBridge.php b/bridges/DribbbleBridge.php
index 5058da6..b1193c9 100644
--- a/bridges/DribbbleBridge.php
+++ b/bridges/DribbbleBridge.php
@@ -19,7 +19,7 @@ favicon-63b2904a073c89b52b19aa08cebc16a154bcf83fee8ecc6439968b1e6db569c7.ico';
$json = $this->loadEmbeddedJsonData($html);
foreach($html->find('li[id^="screenshot-"]') as $shot) {
- $item = [];
+ $item = array();
$additional_data = $this->findJsonForShot($shot, $json);
if ($additional_data === null) {
@@ -38,14 +38,14 @@ favicon-63b2904a073c89b52b19aa08cebc16a154bcf83fee8ecc6439968b1e6db569c7.ico';
$preview_path = $shot->find('picture source', 0)->attr['srcset'];
$item['content'] .= $this->getImageTag($preview_path, $item['title']);
- $item['enclosures'] = [$this->getFullSizeImagePath($preview_path)];
+ $item['enclosures'] = array($this->getFullSizeImagePath($preview_path));
$this->items[] = $item;
}
}
private function loadEmbeddedJsonData($html){
- $json = [];
+ $json = array();
$scripts = $html->find('script');
foreach($scripts as $script) {
diff --git a/bridges/EconomistBridge.php b/bridges/EconomistBridge.php
index 1256be4..94121ac 100644
--- a/bridges/EconomistBridge.php
+++ b/bridges/EconomistBridge.php
@@ -40,7 +40,7 @@ class EconomistBridge extends BridgeAbstract {
if ($nextprev)
$nextprev->outertext = '';
- $section = [ $article->find('h3[itemprop="articleSection"]', 0)->plaintext ];
+ $section = array( $article->find('h3[itemprop="articleSection"]', 0)->plaintext );
$item = array();
$item['title'] = $header->find('span', 0)->innertext . ': '
diff --git a/bridges/ElloBridge.php b/bridges/ElloBridge.php
index 3de167e..8bcfa92 100644
--- a/bridges/ElloBridge.php
+++ b/bridges/ElloBridge.php
@@ -95,7 +95,7 @@ class ElloBridge extends BridgeAbstract {
private function getEnclosures($post, $postData) {
- $assets = [];
+ $assets = array();
foreach($post->links->assets as $asset) {
foreach($postData->linked->assets as $assetLink) {
if($asset == $assetLink->id) {
@@ -124,7 +124,7 @@ class ElloBridge extends BridgeAbstract {
$cacheFac->setWorkingDir(PATH_LIB_CACHES);
$cache = $cacheFac->create(Configuration::getConfig('cache', 'type'));
$cache->setScope(get_called_class());
- $cache->setKey(['key']);
+ $cache->setKey(array('key'));
$key = $cache->loadData();
if($key == null) {
diff --git a/bridges/ElsevierBridge.php b/bridges/ElsevierBridge.php
index 080fe00..01230a9 100644
--- a/bridges/ElsevierBridge.php
+++ b/bridges/ElsevierBridge.php
@@ -3,7 +3,7 @@ class ElsevierBridge extends BridgeAbstract {
const MAINTAINER = 'Pierre Mazière';
const NAME = 'Elsevier journals recent articles';
- const URI = 'http://www.journals.elsevier.com/';
+ const URI = 'https://www.journals.elsevier.com/';
const CACHE_TIMEOUT = 43200; //12h
const DESCRIPTION = 'Returns the recent articles published in Elsevier journals';
diff --git a/bridges/EsquerdaNetBridge.php b/bridges/EsquerdaNetBridge.php
new file mode 100644
index 0000000..f459eb2
--- /dev/null
+++ b/bridges/EsquerdaNetBridge.php
@@ -0,0 +1,70 @@
+<?php
+class EsquerdaNetBridge extends FeedExpander {
+ const MAINTAINER = 'somini';
+ const NAME = 'Esquerda.net';
+ const URI = 'https://www.esquerda.net';
+ const DESCRIPTION = 'Esquerda.net';
+ const PARAMETERS = array(
+ array(
+ 'feed' => array(
+ 'name' => 'Feed',
+ 'type' => 'list',
+ 'defaultValue' => 'Geral',
+ 'values' => array(
+ 'Geral' => 'geral',
+ 'Dossier' => 'artigos-dossier',
+ 'Vídeo' => 'video',
+ 'Opinião' => 'opinioes',
+ 'Rádio' => 'radio',
+ )
+ )
+ )
+ );
+
+ public function getURI() {
+ $type = $this->getInput('feed');
+ return self::URI . '/rss/' . $type;
+ }
+
+ public function getIcon() {
+ return 'https://www.esquerda.net/sites/default/files/favicon_0.ico';
+ }
+
+ public function collectData(){
+ parent::collectExpandableDatas($this->getURI());
+ }
+
+ protected function parseItem($newsItem){
+ # Fix Publish date
+ $badDate = $newsItem->pubDate;
+ preg_match('|(?P<day>\d\d)/(?P<month>\d\d)/(?P<year>\d\d\d\d) - (?P<hour>\d\d):(?P<minute>\d\d)|', $badDate, $d);
+ $newsItem->pubDate = sprintf('%s-%s-%sT%s:%s', $d['year'], $d['month'], $d['day'], $d['hour'], $d['minute']);
+ $item = parent::parseItem($newsItem);
+ # Include all the content
+ $uri = $item['uri'];
+ $html = getSimpleHTMLDOMCached($uri)
+ or returnServerError('Could not load content for ' . $uri);
+ $content = $html->find('div#content div.content', 0);
+ ## Fix author
+ $authorHTML = $html->find('.field-name-field-op-author a', 0);
+ if ($authorHTML) {
+ $item['author'] = $authorHTML->innertext;
+ $authorHTML->remove();
+ }
+ ## Remove crap
+ $content->find('.field-name-addtoany', 0)->remove();
+ ## Fix links
+ $content = defaultLinkTo($content, self::URI);
+ ## Fix Images
+ foreach($content->find('img') as $img) {
+ $altSrc = $img->getAttribute('data-src');
+ if ($altSrc) {
+ $img->setAttribute('src', $altSrc);
+ }
+ $img->width = null;
+ $img->height = null;
+ }
+ $item['content'] = $content;
+ return $item;
+ }
+}
diff --git a/bridges/ExtremeDownloadBridge.php b/bridges/ExtremeDownloadBridge.php
index acdf630..1b4aa9a 100644
--- a/bridges/ExtremeDownloadBridge.php
+++ b/bridges/ExtremeDownloadBridge.php
@@ -1,7 +1,7 @@
<?php
class ExtremeDownloadBridge extends BridgeAbstract {
const NAME = 'Extreme Download';
- const URI = 'https://ww1.extreme-d0wn.com/';
+ const URI = 'https://wvw.extreme-down.xyz/';
const DESCRIPTION = 'Suivi de série sur Extreme Download';
const MAINTAINER = 'sysadminstory';
const PARAMETERS = array(
diff --git a/bridges/FB2Bridge.php b/bridges/FB2Bridge.php
index 2faa321..77ae271 100644
--- a/bridges/FB2Bridge.php
+++ b/bridges/FB2Bridge.php
@@ -2,7 +2,7 @@
class FB2Bridge extends BridgeAbstract {
const MAINTAINER = 'teromene';
- const NAME = 'Facebook Alternate';
+ const NAME = 'Facebook Bridge | Touch Site';
const URI = 'https://www.facebook.com/';
const CACHE_TIMEOUT = 1000;
const DESCRIPTION = 'Input a page title or a profile log. For a profile log,
@@ -12,7 +12,12 @@ class FB2Bridge extends BridgeAbstract {
'u' => array(
'name' => 'Username',
'required' => true
- )
+ ),
+ 'abbrev_name' => array(
+ 'name' => 'Abbreviate author name in title',
+ 'type' => 'checkbox',
+ 'defaultValue' => true,
+ ),
));
public function getIcon() {
@@ -102,12 +107,12 @@ EOD
else
$timestamp = 0;
- $item['uri'] = html_entity_decode('http://touch.facebook.com'
+ $item['uri'] = html_entity_decode('https://touch.facebook.com'
. $content->find("div[class='_52jc _5qc4 _78cz _24u0 _36xo']", 0)->find('a', 0)->getAttribute('href'), ENT_QUOTES);
//Decode images
$imagecleaned = preg_replace_callback('/<i [^>]* style="[^"]*url\(\'(.*?)\'\).*?><\/i>/m', function ($matches) {
- return "<img src='" . str_replace(['\\3a ', '\\3d ', '\\26 '], [':', '=', '&'], $matches[1]) . "' />";
+ return "<img src='" . str_replace(array('\\3a ', '\\3d ', '\\26 '), array(':', '=', '&'), $matches[1]) . "' />";
}, $content);
$content = str_get_html($imagecleaned);
@@ -159,7 +164,11 @@ EOD
$content = preg_replace('/<img src=\'.*?safe_image\.php.*?\' \/>/m', '', $content);
//Remove the double section tags
- $content = str_replace(['<section><section>', '</section></section>'], ['<section>', '</section>'], $content);
+ $content = str_replace(
+ array('<section><section>', '</section></section>'),
+ array('<section>', '</section>'),
+ $content
+ );
//Move the section tag link upper, if it is down
$content = str_get_html($content);
@@ -182,8 +191,10 @@ EOD
$item['content'] = html_entity_decode($content, ENT_QUOTES);
$title = $author;
- if (strlen($title) > 24)
- $title = substr($title, 0, strpos(wordwrap($title, 24), "\n")) . '...';
+ if ($this->getInput('abbrev_name') === true) {
+ if (strlen($title) > 24)
+ $title = substr($title, 0, strpos(wordwrap($title, 24), "\n")) . '...';
+ }
$title = $title . ' | ' . strip_tags($content);
if (strlen($title) > 64)
$title = substr($title, 0, strpos(wordwrap($title, 64), "\n")) . '...';
@@ -281,10 +292,20 @@ EOD
}
public function getName(){
- return (isset($this->name) ? $this->name . ' - ' : '') . 'Facebook Bridge';
+ $username = $this->getInput('u');
+ if (isset($username)) {
+ return $this->getInput('u') . ' | Facebook';
+ } else {
+ return self::NAME;
+ }
}
public function getURI(){
- return 'http://facebook.com';
+ $username = $this->getInput('u');
+ if (isset($username)) {
+ return 'https://facebook.com/' . $this->getInput('u') . '/posts';
+ } else {
+ return self::URI;
+ }
}
}
diff --git a/bridges/FacebookBridge.php b/bridges/FacebookBridge.php
index 08b3a38..5ce67f9 100644
--- a/bridges/FacebookBridge.php
+++ b/bridges/FacebookBridge.php
@@ -2,7 +2,7 @@
class FacebookBridge extends BridgeAbstract {
const MAINTAINER = 'teromene, logmanoriginal';
- const NAME = 'Facebook Bridge';
+ const NAME = 'Facebook Bridge | Main Site';
const URI = 'https://www.facebook.com/';
const CACHE_TIMEOUT = 300; // 5min
const DESCRIPTION = 'Input a page title or a profile log. For a profile log,
@@ -66,14 +66,13 @@ class FacebookBridge extends BridgeAbstract {
case 'User':
if(!empty($this->authorName)) {
- return isset($this->extraInfos['name']) ? $this->extraInfos['name'] : $this->authorName
- . ' - ' . static::NAME;
+ return isset($this->extraInfos['name']) ? $this->extraInfos['name'] : $this->authorName;
}
break;
case 'Group':
if(!empty($this->groupName)) {
- return $this->groupName . ' - ' . static::NAME;
+ return $this->groupName;
}
break;
@@ -82,6 +81,34 @@ class FacebookBridge extends BridgeAbstract {
return parent::getName();
}
+ public function detectParameters($url){
+ $params = array();
+
+ // By profile
+ $regex = '/^(https?:\/\/)?(www\.)?facebook\.com\/profile\.php\?id\=([^\/?&\n]+)?(.*)/';
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['u'] = urldecode($matches[3]);
+ return $params;
+ }
+
+ // By group
+ $regex = '/^(https?:\/\/)?(www\.)?facebook\.com\/groups\/([^\/?\n]+)?(.*)/';
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['g'] = urldecode($matches[3]);
+ return $params;
+ }
+
+ // By username
+ $regex = '/^(https?:\/\/)?(www\.)?facebook\.com\/([^\/?\n]+)/';
+
+ if(preg_match($regex, $url, $matches) > 0) {
+ $params['u'] = urldecode($matches[3]);
+ return $params;
+ }
+
+ return null;
+ }
+
public function getURI() {
$uri = self::URI;
@@ -674,8 +701,15 @@ EOD;
$uri = $post->find('abbr')[0]->parent()->getAttribute('href');
- if (false !== strpos($uri, '?')) {
- $uri = substr($uri, 0, strpos($uri, '?'));
+ // Extract fbid and patch link
+ if (strpos($uri, '?') !== false) {
+ $query = substr($uri, strpos($uri, '?') + 1);
+ parse_str($query, $query_params);
+ if (isset($query_params['story_fbid'])) {
+ $uri = self::URI . $query_params['story_fbid'];
+ } else {
+ $uri = substr($uri, 0, strpos($uri, '?'));
+ }
}
//Build and add final item
diff --git a/bridges/FreeCodeCampBridge.php b/bridges/FreeCodeCampBridge.php
new file mode 100644
index 0000000..da0b5c7
--- /dev/null
+++ b/bridges/FreeCodeCampBridge.php
@@ -0,0 +1,27 @@
+<?php
+class FreeCodeCampBridge extends FeedExpander {
+
+ const MAINTAINER = 'IceWreck';
+ const NAME = 'FreeCodecamp Bridge';
+ const URI = 'https://www.freecodecamp.org';
+ const CACHE_TIMEOUT = 3600;
+ const DESCRIPTION = 'RSS feed for FreeCodeCamp';
+ // Freecodecamp removed their old full content rss feed and replaced it with one liner content.
+
+ public function collectData(){
+ $this->collectExpandableDatas('https://www.freecodecamp.org/news/rss/', 15);
+ }
+
+ protected function parseItem($newsItem){
+ $item = parent::parseItem($newsItem);
+ // $articlePage gets the entire page's contents
+ $articlePage = getSimpleHTMLDOM($newsItem->link);
+ // figure contain's the main article image
+ $article = $articlePage->find('figure', 0);
+ // the actual article
+ foreach($articlePage->find('.post-full-content') as $element)
+ $article = $article . $element;
+ $item['content'] = $article;
+ return $item;
+ }
+}
diff --git a/bridges/FurAffinityUserBridge.php b/bridges/FurAffinityUserBridge.php
new file mode 100644
index 0000000..fd8a61f
--- /dev/null
+++ b/bridges/FurAffinityUserBridge.php
@@ -0,0 +1,110 @@
+<?php
+class FurAffinityUserBridge extends BridgeAbstract {
+ const NAME = 'FurAffinity User Gallery';
+ const URI = 'https://www.furaffinity.net';
+ const MAINTAINER = 'CyberJacob';
+ const PARAMETERS = array(
+ array(
+ 'searchUsername' => array(
+ 'name' => 'Search Username',
+ 'type' => 'text',
+ 'required' => true,
+ 'title' => 'Username to fetch the gallery for'
+ ),
+ 'loginUsername' => array(
+ 'name' => 'Login Username',
+ 'type' => 'text',
+ 'required' => true
+ ),
+ 'loginPassword' => array(
+ 'name' => 'Login Password',
+ 'type' => 'text',
+ 'required' => true
+ )
+ )
+ );
+
+ public function collectData() {
+ $cookies = self::login();
+ $url = self::URI . '/gallery/' . $this->getInput('searchUsername');
+
+ $html = getSimpleHTMLDOM($url, $cookies)
+ or returnServerError('Could not load the user\'s galary page.');
+
+ $submissions = $html->find('section[id=gallery-gallery]', 0)->find('figure');
+ foreach($submissions as $submission) {
+ $item = array();
+ $item['title'] = $submission->find('figcaption', 0)->find('a', 0)->plaintext;
+
+ $thumbnail = $submission->find('a', 0);
+ $thumbnail->href = self::URI . $thumbnail->href;
+
+ $item['content'] = $submission->find('a', 0);
+
+ $this->items[] = $item;
+ }
+ }
+
+ public function getName() {
+ return self::NAME . ' for ' . $this->getInput('searchUsername');
+ }
+
+ public function getURI() {
+ return self::URI . '/user/' . $this->getInput('searchUsername');
+ }
+
+ private function login() {
+ $ch = curl_init(self::URI . '/login/');
+ curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
+ curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
+
+ curl_setopt($ch, CURLOPT_USERAGENT, ini_get('user_agent'));
+ curl_setopt($ch, CURLOPT_ENCODING, '');
+ curl_setopt($ch, CURLOPT_PROTOCOLS, CURLPROTO_HTTP | CURLPROTO_HTTPS);
+
+ $fields = implode('&', array(
+ 'action=login',
+ 'retard_protection=1',
+ 'name=' . urlencode($this->getInput('loginUsername')),
+ 'pass=' . urlencode($this->getInput('loginPassword')),
+ 'login=Login to Faraffinity'
+ ));
+
+ curl_setopt($ch, CURLOPT_POST, 5);
+ curl_setopt($ch, CURLOPT_POSTFIELDS, $fields);
+
+ if(defined('PROXY_URL') && !defined('NOPROXY')) {
+ curl_setopt($ch, CURLOPT_PROXY, PROXY_URL);
+ }
+
+ curl_setopt($ch, CURLOPT_HEADER, true);
+ curl_setopt($ch, CURLINFO_HEADER_OUT, true);
+
+ $data = curl_exec($ch);
+
+ $errorCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
+
+ $curlError = curl_error($ch);
+ $curlErrno = curl_errno($ch);
+ $curlInfo = curl_getinfo($ch);
+
+ if($data === false)
+ fDebug::log("Cant't download {$url} cUrl error: {$curlError} ({$curlErrno})");
+
+ curl_close($ch);
+
+ if($errorCode != 200) {
+ returnServerError(error_get_last());
+ } else {
+ preg_match_all('/^Set-Cookie:\s*([^;]*)/mi', $data, $matches);
+ $cookies = array();
+
+ foreach($matches[1] as $item) {
+ parse_str($item, $cookie);
+ $cookies = array_merge($cookies, $cookie);
+ }
+
+ return $cookies;
+ }
+ }
+}
diff --git a/bridges/GQMagazineBridge.php b/bridges/GQMagazineBridge.php
index 2884ab6..14a9a56 100644
--- a/bridges/GQMagazineBridge.php
+++ b/bridges/GQMagazineBridge.php
@@ -117,7 +117,7 @@ class GQMagazineBridge extends BridgeAbstract
*/
private function loadFullArticle($uri){
$html = getSimpleHTMLDOMCached($uri);
- return $html->find('section[data-test-id=ArticleBodyContent]', 0);
+ return $html->find('section[data-test-id=MainContentWrapper]', 0);
}
/**
diff --git a/bridges/GiphyBridge.php b/bridges/GiphyBridge.php
index 26d1eba..202bbbb 100644
--- a/bridges/GiphyBridge.php
+++ b/bridges/GiphyBridge.php
@@ -5,7 +5,7 @@ class GiphyBridge extends BridgeAbstract {
const MAINTAINER = 'kraoc';
const NAME = 'Giphy Bridge';
- const URI = 'http://giphy.com/';
+ const URI = 'https://giphy.com/';
const CACHE_TIMEOUT = 300; //5min
const DESCRIPTION = 'Bridge for giphy.com';
diff --git a/bridges/GoogleSearchBridge.php b/bridges/GoogleSearchBridge.php
index c3d9561..e02aaeb 100644
--- a/bridges/GoogleSearchBridge.php
+++ b/bridges/GoogleSearchBridge.php
@@ -25,13 +25,10 @@ class GoogleSearchBridge extends BridgeAbstract {
public function collectData(){
$html = '';
- $html = getSimpleHTMLDOM(self::URI
- . 'search?q='
- . urlencode($this->getInput('q'))
- . '&num=100&complete=0&tbs=qdr:y,sbd:1')
+ $html = getSimpleHTMLDOM($this->getURI())
or returnServerError('No results for this query.');
- $emIsRes = $html->find('div[id=ires]', 0);
+ $emIsRes = $html->find('div[id=res]', 0);
if(!is_null($emIsRes)) {
foreach($emIsRes->find('div[class=g]') as $element) {
@@ -54,6 +51,17 @@ class GoogleSearchBridge extends BridgeAbstract {
}
}
+ public function getURI() {
+ if (!is_null($this->getInput('q'))) {
+ return self::URI
+ . 'search?q='
+ . urlencode($this->getInput('q'))
+ . '&num=100&complete=0&tbs=qdr:y,sbd:1';
+ }
+
+ return parent::getURI();
+ }
+
public function getName(){
if(!is_null($this->getInput('q'))) {
return $this->getInput('q') . ' - Google search';
diff --git a/bridges/HDWallpapersBridge.php b/bridges/HDWallpapersBridge.php
index f1579e0..16c08e7 100644
--- a/bridges/HDWallpapersBridge.php
+++ b/bridges/HDWallpapersBridge.php
@@ -2,7 +2,7 @@
class HDWallpapersBridge extends BridgeAbstract {
const MAINTAINER = 'nel50n';
const NAME = 'HD Wallpapers Bridge';
- const URI = 'http://www.hdwallpapers.in/';
+ const URI = 'https://www.hdwallpapers.in/';
const CACHE_TIMEOUT = 43200; //12h
const DESCRIPTION = 'Returns the latests wallpapers from HDWallpapers';
@@ -72,7 +72,7 @@ class HDWallpapersBridge extends BridgeAbstract {
public function getName(){
if(!is_null($this->getInput('c')) && !is_null($this->getInput('r'))) {
return 'HDWallpapers - '
- . str_replace(['__', '_'], [' & ', ' '], $this->getInput('c'))
+ . str_replace(array('__', '_'), array(' & ', ' '), $this->getInput('c'))
. ' ['
. $this->getInput('r')
. ']';
diff --git a/bridges/InstagramBridge.php b/bridges/InstagramBridge.php
index 77a48e6..679c4c0 100644
--- a/bridges/InstagramBridge.php
+++ b/bridges/InstagramBridge.php
@@ -32,11 +32,15 @@ class InstagramBridge extends BridgeAbstract {
'required' => false,
'values' => array(
'All' => 'all',
- 'Story' => 'story',
'Video' => 'video',
'Picture' => 'picture',
+ 'Multiple' => 'multiple',
),
'defaultValue' => 'all'
+ ),
+ 'direct_links' => array(
+ 'name' => 'Use direct media links',
+ 'type' => 'checkbox',
)
)
@@ -44,7 +48,7 @@ class InstagramBridge extends BridgeAbstract {
const USER_QUERY_HASH = '58b6785bea111c67129decbe6a448951';
const TAG_QUERY_HASH = '174a5243287c5f3a7de741089750ab3b';
- const STORY_QUERY_HASH = '865589822932d1b43dfe312121dd353a';
+ const SHORTCODE_QUERY_HASH = '865589822932d1b43dfe312121dd353a';
protected function getInstagramUserId($username) {
@@ -54,7 +58,7 @@ class InstagramBridge extends BridgeAbstract {
$cacheFac->setWorkingDir(PATH_LIB_CACHES);
$cache = $cacheFac->create(Configuration::getConfig('cache', 'type'));
$cache->setScope(get_called_class());
- $cache->setKey([$username]);
+ $cache->setKey(array($username));
$key = $cache->loadData();
if($key == null) {
@@ -75,10 +79,7 @@ class InstagramBridge extends BridgeAbstract {
}
public function collectData(){
-
- if(is_null($this->getInput('u')) && $this->getInput('media_type') == 'story') {
- returnClientError('Stories are not supported for hashtags nor locations!');
- }
+ $directLink = !is_null($this->getInput('direct_links')) && $this->getInput('direct_links');
$data = $this->getInstagramJSON($this->getURI());
@@ -93,22 +94,18 @@ class InstagramBridge extends BridgeAbstract {
foreach($userMedia as $media) {
$media = $media->node;
- if(!is_null($this->getInput('u'))) {
- switch($this->getInput('media_type')) {
- case 'all': break;
- case 'video':
- if($media->__typename != 'GraphVideo') continue 2;
- break;
- case 'picture':
- if($media->__typename != 'GraphImage') continue 2;
- break;
- case 'story':
- if($media->__typename != 'GraphSidecar') continue 2;
- break;
- default: break;
- }
- } else {
- if($this->getInput('media_type') == 'video' && !$media->is_video) continue;
+ switch($this->getInput('media_type')) {
+ case 'all': break;
+ case 'video':
+ if($media->__typename != 'GraphVideo' || !$media->is_video) continue 2;
+ break;
+ case 'picture':
+ if($media->__typename != 'GraphImage') continue 2;
+ break;
+ case 'multiple':
+ if($media->__typename != 'GraphSidecar') continue 2;
+ break;
+ default: break;
}
$item = array();
@@ -118,69 +115,105 @@ class InstagramBridge extends BridgeAbstract {
$item['author'] = $media->owner->username;
}
- if (isset($media->edge_media_to_caption->edges[0]->node->text)) {
- $textContent = $media->edge_media_to_caption->edges[0]->node->text;
- } else {
- $textContent = '(no text)';
- }
+ $textContent = $this->getTextContent($media);
- $item['title'] = ($media->is_video ? '▶ ' : '') . trim($textContent);
+ $item['title'] = ($media->is_video ? '▶ ' : '') . $textContent;
$titleLinePos = strpos(wordwrap($item['title'], 120), "\n");
if ($titleLinePos != false) {
$item['title'] = substr($item['title'], 0, $titleLinePos) . '...';
}
- if(!is_null($this->getInput('u')) && $media->__typename == 'GraphSidecar') {
-
- $data = $this->getInstagramStory($item['uri']);
- $item['content'] = $data[0];
- $item['enclosures'] = $data[1];
- } else {
- $mediaURI = self::URI . 'p/' . $media->shortcode . '/media?size=l';
- $item['content'] = '<a href="' . htmlentities($item['uri']) . '" target="_blank">';
- $item['content'] .= '<img src="' . htmlentities($mediaURI) . '" alt="' . $item['title'] . '" />';
- $item['content'] .= '</a><br><br>' . nl2br(htmlentities($textContent));
- $item['enclosures'] = array($mediaURI);
+ switch($media->__typename) {
+ case 'GraphSidecar':
+ $data = $this->getInstagramSidecarData($item['uri'], $item['title']);
+ $item['content'] = $data[0];
+ $item['enclosures'] = $data[1];
+ break;
+ case 'GraphImage':
+ if($directLink) {
+ $mediaURI = $media->display_url;
+ } else {
+ $mediaURI = self::URI . 'p/' . $media->shortcode . '/media?size=l';
+ }
+ $item['content'] = '<a href="' . htmlentities($item['uri']) . '" target="_blank">';
+ $item['content'] .= '<img src="' . htmlentities($mediaURI) . '" alt="' . $item['title'] . '" />';
+ $item['content'] .= '</a><br><br>' . nl2br(htmlentities($textContent));
+ $item['enclosures'] = array($mediaURI);
+ break;
+ case 'GraphVideo':
+ $data = $this->getInstagramVideoData($item['uri']);
+ $item['content'] = $data[0];
+ if($directLink) {
+ $item['enclosures'] = $data[1];
+ } else {
+ $item['enclosures'] = array(self::URI . 'p/' . $media->shortcode . '/media?size=l');
+ }
+ break;
+ default: break;
}
-
$item['timestamp'] = $media->taken_at_timestamp;
$this->items[] = $item;
}
}
- protected function getInstagramStory($uri) {
-
- $shortcode = explode('/', $uri)[4];
- $data = getContents(self::URI .
- 'graphql/query/?query_hash=' .
- self::STORY_QUERY_HASH .
- '&variables={"shortcode"%3A"' .
- $shortcode .
- '"}');
+ // returns Sidecar(a post which has multiple media)'s contents and enclosures
+ protected function getInstagramSidecarData($uri, $postTitle) {
+ $mediaInfo = $this->getSinglePostData($uri);
- $mediaInfo = json_decode($data)->data->shortcode_media;
+ $textContent = $this->getTextContent($mediaInfo);
- //Process the first element, that isn't in the node graph
- if (count($mediaInfo->edge_media_to_caption->edges) > 0) {
- $caption = $mediaInfo->edge_media_to_caption->edges[0]->node->text;
- } else {
- $caption = '';
+ $enclosures = array();
+ $content = '';
+ foreach($mediaInfo->edge_sidecar_to_children->edges as $singleMedia) {
+ $singleMedia = $singleMedia->node;
+ if($singleMedia->is_video) {
+ if(in_array($singleMedia->video_url, $enclosures)) continue; // check if not added yet
+ $content .= '<video controls><source src="' . $singleMedia->video_url . '" type="video/mp4"></video><br>';
+ array_push($enclosures, $singleMedia->video_url);
+ } else {
+ if(in_array($singleMedia->display_url, $enclosures)) continue; // check if not added yet
+ $content .= '<a href="' . $singleMedia->display_url . '" target="_blank">';
+ $content .= '<img src="' . $singleMedia->display_url . '" alt="' . $postTitle . '" />';
+ $content .= '</a><br>';
+ array_push($enclosures, $singleMedia->display_url);
+ }
}
+ $content .= '<br>' . nl2br(htmlentities($textContent));
- $enclosures = [$mediaInfo->display_url];
- $content = '<img src="' . htmlentities($mediaInfo->display_url) . '" alt="' . $caption . '" />';
+ return array($content, $enclosures);
+ }
- foreach($mediaInfo->edge_sidecar_to_children->edges as $media) {
- $display_url = $media->node->display_url;
- if(!in_array($display_url, $enclosures)) { // add only if not added yet
- $content .= '<img src="' . htmlentities($display_url) . '" alt="' . $caption . '" />';
- $enclosures[] = $display_url;
- }
+ // returns Video post's contents and enclosures
+ protected function getInstagramVideoData($uri) {
+ $mediaInfo = $this->getSinglePostData($uri);
+
+ $textContent = $this->getTextContent($mediaInfo);
+ $content = '<video controls><source src="' . $mediaInfo->video_url . '" type="video/mp4"></video><br>';
+ $content .= '<br>' . nl2br(htmlentities($textContent));
+
+ return array($content, array($mediaInfo->video_url));
+ }
+
+ protected function getTextContent($media) {
+ $textContent = '(no text)';
+ //Process the first element, that isn't in the node graph
+ if (count($media->edge_media_to_caption->edges) > 0) {
+ $textContent = trim($media->edge_media_to_caption->edges[0]->node->text);
}
+ return $textContent;
+ }
- return [$content, $enclosures];
+ protected function getSinglePostData($uri) {
+ $shortcode = explode('/', $uri)[4];
+ $data = getContents(self::URI .
+ 'graphql/query/?query_hash=' .
+ self::SHORTCODE_QUERY_HASH .
+ '&variables={"shortcode"%3A"' .
+ $shortcode .
+ '"}');
+ return json_decode($data)->data->shortcode_media;
}
protected function getInstagramJSON($uri) {
diff --git a/bridges/JapanExpoBridge.php b/bridges/JapanExpoBridge.php
index 1790171..7906ec0 100644
--- a/bridges/JapanExpoBridge.php
+++ b/bridges/JapanExpoBridge.php
@@ -19,28 +19,6 @@ class JapanExpoBridge extends BridgeAbstract {
public function collectData(){
- function frenchPubDateToTimestamp($date_to_parse) {
- return strtotime(
- strtr(
- strtolower(str_replace('Publié le ', '', $date_to_parse)),
- array(
- 'janvier' => 'jan',
- 'février' => 'feb',
- 'mars' => 'march',
- 'avril' => 'apr',
- 'mai' => 'may',
- 'juin' => 'jun',
- 'juillet' => 'jul',
- 'août' => 'aug',
- 'septembre' => 'sep',
- 'octobre' => 'oct',
- 'novembre' => 'nov',
- 'décembre' => 'dec'
- )
- )
- );
- }
-
$convert_article_images = function($matches){
if(is_array($matches) && count($matches) > 1) {
return '<img src="' . $matches[1] . '" />';
@@ -82,7 +60,7 @@ class JapanExpoBridge extends BridgeAbstract {
$content = $headings . $article;
} else {
$date_text = $element->find('span.date', 0)->plaintext;
- $timestamp = frenchPubDateToTimestamp($date_text);
+ $timestamp = $this->frenchPubDateToTimestamp($date_text);
$title = trim($element->find('span._title', 0)->plaintext);
$content = '<img src="'
. $thumbnail
@@ -103,4 +81,26 @@ class JapanExpoBridge extends BridgeAbstract {
$count++;
}
}
+
+ private function frenchPubDateToTimestamp($date_to_parse) {
+ return strtotime(
+ strtr(
+ strtolower(str_replace('Publié le ', '', $date_to_parse)),
+ array(
+ 'janvier' => 'jan',
+ 'février' => 'feb',
+ 'mars' => 'march',
+ 'avril' => 'apr',
+ 'mai' => 'may',
+ 'juin' => 'jun',
+ 'juillet' => 'jul',
+ 'août' => 'aug',
+ 'septembre' => 'sep',
+ 'octobre' => 'oct',
+ 'novembre' => 'nov',
+ 'décembre' => 'dec'
+ )
+ )
+ );
+ }
}
diff --git a/bridges/KonachanBridge.php b/bridges/KonachanBridge.php
index 4250e8b..2aada37 100644
--- a/bridges/KonachanBridge.php
+++ b/bridges/KonachanBridge.php
@@ -5,7 +5,7 @@ class KonachanBridge extends MoebooruBridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Konachan';
- const URI = 'http://konachan.com/';
+ const URI = 'https://konachan.com/';
const DESCRIPTION = 'Returns images from given page';
}
diff --git a/bridges/KununuBridge.php b/bridges/KununuBridge.php
index 7cc4af6..e26292d 100644
--- a/bridges/KununuBridge.php
+++ b/bridges/KununuBridge.php
@@ -34,6 +34,12 @@ class KununuBridge extends BridgeAbstract {
'name' => 'Include benefits',
'type' => 'checkbox',
'title' => 'Activate to include benefits in the feed'
+ ),
+ 'limit' => array(
+ 'name' => 'Limit',
+ 'type' => 'number',
+ 'defaultValue' => 3,
+ 'title' => "Maximum number of items to return in the feed.\n0 = unlimited"
)
),
array(
@@ -108,6 +114,8 @@ class KununuBridge extends BridgeAbstract {
$articles = $section->find('article')
or returnServerError('Unable to find articles!');
+ $limit = $this->getInput('limit') ?: 0;
+
// Go through all articles
foreach($articles as $article) {
@@ -141,6 +149,8 @@ class KununuBridge extends BridgeAbstract {
$this->items[] = $item;
+ if ($limit > 0 && count($this->items) >= $limit) break;
+
}
}
diff --git a/bridges/LeBonCoinBridge.php b/bridges/LeBonCoinBridge.php
index 519fc91..fc1432e 100644
--- a/bridges/LeBonCoinBridge.php
+++ b/bridges/LeBonCoinBridge.php
@@ -431,11 +431,11 @@ class LeBonCoinBridge extends BridgeAbstract {
);
if($this->getInput('region') != '') {
- $requestJson->filters->location['regions'] = [$this->getInput('region')];
+ $requestJson->filters->location['regions'] = array($this->getInput('region'));
}
if($this->getInput('department') != '') {
- $requestJson->filters->location['departments'] = [$this->getInput('department')];
+ $requestJson->filters->location['departments'] = array($this->getInput('department'));
}
if($this->getInput('cities') != '') {
@@ -467,7 +467,7 @@ class LeBonCoinBridge extends BridgeAbstract {
}
if($this->getInput('estate') != '') {
- $requestJson->filters->enums['real_estate_type'] = [$this->getInput('estate')];
+ $requestJson->filters->enums['real_estate_type'] = array($this->getInput('estate'));
}
if($this->getInput('roomsmin') != ''
@@ -526,7 +526,7 @@ class LeBonCoinBridge extends BridgeAbstract {
}
if($this->getInput('fuel') != '') {
- $requestJson->filters->enums['fuel'] = [$this->getInput('fuel')];
+ $requestJson->filters->enums['fuel'] = array($this->getInput('fuel'));
}
$requestJson->limit = 30;
diff --git a/bridges/ListverseBridge.php b/bridges/ListverseBridge.php
new file mode 100644
index 0000000..f597c0b
--- /dev/null
+++ b/bridges/ListverseBridge.php
@@ -0,0 +1,22 @@
+<?php
+class ListverseBridge extends FeedExpander {
+
+ const MAINTAINER = 'IceWreck';
+ const NAME = 'Listverse Bridge';
+ const URI = 'https://listverse.com/';
+ const CACHE_TIMEOUT = 3600;
+ const DESCRIPTION = 'RSS feed for Listverse';
+
+ public function collectData(){
+ $this->collectExpandableDatas('https://listverse.com/feed/', 15);
+ }
+
+ protected function parseItem($newsItem){
+ $item = parent::parseItem($newsItem);
+ // $articlePage gets the entire page's contents
+ $articlePage = getSimpleHTMLDOM($newsItem->link);
+ $article = $articlePage->find('#articlecontentonly', 0);
+ $item['content'] = $article;
+ return $item;
+ }
+}
diff --git a/bridges/MangareaderBridge.php b/bridges/MangareaderBridge.php
index 9ecb0fe..a41113a 100644
--- a/bridges/MangareaderBridge.php
+++ b/bridges/MangareaderBridge.php
@@ -3,7 +3,7 @@ class MangareaderBridge extends BridgeAbstract {
const MAINTAINER = 'logmanoriginal';
const NAME = 'Mangareader Bridge';
- const URI = 'http://www.mangareader.net';
+ const URI = 'https://www.mangareader.net';
const CACHE_TIMEOUT = 10800; // 3h
const DESCRIPTION = 'Returns the latest updates, popular mangas or manga updates (new chapters)';
diff --git a/bridges/MediapartBridge.php b/bridges/MediapartBridge.php
index 15d1d3e..f7fff4a 100644
--- a/bridges/MediapartBridge.php
+++ b/bridges/MediapartBridge.php
@@ -30,29 +30,34 @@ class MediapartBridge extends FeedExpander {
protected function parseItem($newsItem) {
$item = parent::parseItem($newsItem);
- // Enable single page mode?
- if ($this->getInput('single_page_mode') === true) {
- $item['uri'] .= '?onglet=full';
- }
+ // Mediapart provide multiple type of contents.
+ // We only process items relative to the newspaper
+ // See issue #1292 - https://github.com/RSS-Bridge/rss-bridge/issues/1292
+ if (strpos($item['uri'], self::URI . 'journal/') === 0) {
+ // Enable single page mode?
+ if ($this->getInput('single_page_mode') === true) {
+ $item['uri'] .= '?onglet=full';
+ }
+
+ // If a session cookie is defined, get the full article
+ $mpsessid = $this->getInput('mpsessid');
+ if (!empty($mpsessid)) {
+ // Set the session cookie
+ $opt = array();
+ $opt[CURLOPT_COOKIE] = 'MPSESSID=' . $mpsessid;
+
+ // Get the page
+ $articlePage = getSimpleHTMLDOM(
+ $newsItem->link . '?onglet=full',
+ array(),
+ $opt);
- // If a session cookie is defined, get the full article
- $mpsessid = $this->getInput('mpsessid');
- if (!empty($mpsessid)) {
- // Set the session cookie
- $opt = array();
- $opt[CURLOPT_COOKIE] = 'MPSESSID=' . $mpsessid;
-
- // Get the page
- $articlePage = getSimpleHTMLDOM(
- $newsItem->link . '?onglet=full',
- array(),
- $opt);
-
- // Extract the article content
- $content = $articlePage->find('div.content-article', 0)->innertext;
- $content = sanitize($content);
- $content = defaultLinkTo($content, static::URI);
- $item['content'] .= $content;
+ // Extract the article content
+ $content = $articlePage->find('div.content-article', 0)->innertext;
+ $content = sanitize($content);
+ $content = defaultLinkTo($content, static::URI);
+ $item['content'] .= $content;
+ }
}
return $item;
diff --git a/bridges/N26Bridge.php b/bridges/N26Bridge.php
index dd1c423..ac43756 100644
--- a/bridges/N26Bridge.php
+++ b/bridges/N26Bridge.php
@@ -15,11 +15,11 @@ class N26Bridge extends BridgeAbstract
public function collectData()
{
- $html = getSimpleHTMLDOM(self::URI . '/en-fr/blog-archive')
+ $html = getSimpleHTMLDOM(self::URI . '/en-eu/blog-archive')
or returnServerError('Error while downloading the website content');
- foreach($html->find('div.ga') as $article) {
- $item = [];
+ foreach($html->find('div[class="ag ah ai aj bs bt dx ea fo gx ie if ih ii ij ik s"]') as $article) {
+ $item = array();
$item['uri'] = self::URI . $article->find('h2 a', 0)->href;
$item['title'] = $article->find('h2 a', 0)->plaintext;
@@ -27,9 +27,9 @@ class N26Bridge extends BridgeAbstract
$fullArticle = getSimpleHTMLDOM($item['uri'])
or returnServerError('Error while downloading the full article');
- $dateElement = $fullArticle->find('span[class="fk fl de ch fm by"]', 0);
+ $dateElement = $fullArticle->find('time', 0);
$item['timestamp'] = strtotime($dateElement->plaintext);
- $item['content'] = $fullArticle->find('main article', 0)->innertext;
+ $item['content'] = $fullArticle->find('div[class="af ag ah ai an"]', 1)->innertext;
$this->items[] = $item;
}
diff --git a/bridges/NFLRUSBridge.php b/bridges/NFLRUSBridge.php
new file mode 100644
index 0000000..739f4ab
--- /dev/null
+++ b/bridges/NFLRUSBridge.php
@@ -0,0 +1,60 @@
+<?php
+class NFLRUSBridge extends BridgeAbstract {
+
+ const NAME = 'NFLRUS';
+ const URI = 'http://nflrus.ru/';
+ const DESCRIPTION = 'Returns the recent articles published on nflrus.ru';
+ const MAINTAINER = 'Maxim Shpak';
+
+ private function getEnglishMonth($month) {
+ $months = array(
+ 'Января' => 'January',
+ 'Февраля' => 'February',
+ 'Марта' => 'March',
+ 'Апреля' => 'April',
+ 'Мая' => 'May',
+ 'Июня' => 'June',
+ 'Июля' => 'July',
+ 'Августа' => 'August',
+ 'Сентября' => 'September',
+ 'Октября' => 'October',
+ 'Ноября' => 'November',
+ 'Декабря' => 'December',
+ );
+
+ if (isset($months[$month])) {
+ return $months[$month];
+ }
+ return false;
+ }
+
+ private function extractArticleTimestamp($article) {
+ $time = $article->find('time', 0);
+ if($time) {
+ $timestring = trim($time->plaintext);
+ $parts = explode(' ', $timestring);
+ $month = $this->getEnglishMonth($parts[1]);
+ if ($month) {
+ $timestring = $parts[0] . ' ' . $month . ' ' . $parts[2];
+ return strtotime($timestring);
+ }
+ }
+ return 0;
+ }
+
+ public function collectData() {
+ $html = getSimpleHTMLDOM(self::URI)
+ or returnServerError('Unable to get any articles from NFLRUS');
+ $html = defaultLinkTo($html, self::URI);
+
+ foreach($html->find('article') as $article) {
+ $item = array();
+ $item['uri'] = $article->find('.b-article__title a', 0)->href;
+ $item['title'] = $article->find('.b-article__title a', 0)->plaintext;
+ $item['author'] = $article->find('.link-author', 0)->plaintext;
+ $item['timestamp'] = $this->extractArticleTimestamp($article);
+ $item['content'] = $article->find('div', 0)->innertext;
+ $this->items[] = $item;
+ }
+ }
+}
diff --git a/bridges/NiceMatinBridge.php b/bridges/NiceMatinBridge.php
index 117c779..b0af760 100644
--- a/bridges/NiceMatinBridge.php
+++ b/bridges/NiceMatinBridge.php
@@ -3,7 +3,7 @@ class NiceMatinBridge extends FeedExpander {
const MAINTAINER = 'pit-fgfjiudghdf';
const NAME = 'NiceMatin';
- const URI = 'http://www.nicematin.com/';
+ const URI = 'https://www.nicematin.com/';
const DESCRIPTION = 'Returns the 10 newest posts from NiceMatin (full text)';
public function collectData(){
diff --git a/bridges/NineGagBridge.php b/bridges/NineGagBridge.php
index e726c73..939ff38 100644
--- a/bridges/NineGagBridge.php
+++ b/bridges/NineGagBridge.php
@@ -17,6 +17,15 @@ class NineGagBridge extends BridgeAbstract {
'Fresh' => 'fresh',
),
),
+ 'video' => array(
+ 'name' => 'Filter Video',
+ 'type' => 'list',
+ 'values' => array(
+ 'NotFiltred' => 'none',
+ 'VideoFiltred' => 'without',
+ 'VideoOnly' => 'only',
+ ),
+ ),
'p' => array(
'name' => 'Pages',
'type' => 'number',
@@ -121,13 +130,32 @@ class NineGagBridge extends BridgeAbstract {
}
foreach ($posts as $post) {
- $item['uri'] = $post['url'];
- $item['title'] = $post['title'];
- $item['content'] = self::getContent($post);
- $item['categories'] = self::getCategories($post);
- $item['timestamp'] = self::getTimestamp($post);
+ $AvoidElement = false;
+ switch ($this->getInput('video')) {
+ case 'without':
+ if ($post['type'] === 'Animated') {
+ $AvoidElement = true;
+ }
+ break;
+ case 'only':
+ echo $post['type'];
+ if ($post['type'] !== 'Animated') {
+ $AvoidElement = true;
+ }
+ break;
+ case 'none': default:
+ break;
+ }
+
+ if (!$AvoidElement) {
+ $item['uri'] = $post['url'];
+ $item['title'] = $post['title'];
+ $item['content'] = self::getContent($post);
+ $item['categories'] = self::getCategories($post);
+ $item['timestamp'] = self::getTimestamp($post);
- $this->items[] = $item;
+ $this->items[] = $item;
+ }
}
}
diff --git a/bridges/WhydBridge.php b/bridges/OpenwhydBridge.php
index 04d0b30..f80cb06 100644
--- a/bridges/WhydBridge.php
+++ b/bridges/OpenwhydBridge.php
@@ -1,9 +1,9 @@
<?php
-class WhydBridge extends BridgeAbstract {
+class OpenwhydBridge extends BridgeAbstract {
const MAINTAINER = 'kranack';
- const NAME = 'Whyd Bridge';
- const URI = 'http://www.whyd.com/';
+ const NAME = 'Openwhyd Bridge';
+ const URI = 'https://openwhyd.org';
const CACHE_TIMEOUT = 600; // 10min
const DESCRIPTION = 'Returns 10 newest music from user profile';
@@ -17,8 +17,7 @@ class WhydBridge extends BridgeAbstract {
private $userName = '';
public function getIcon() {
- return self::URI . 'assets/favicons/
-32-6b62a9f14d5e1a9213090d8f00f286bba3a6022381a76390d1d0926493b12593.png?v=6';
+ return self::URI . '/images/favicon.ico';
}
public function collectData(){
@@ -26,11 +25,11 @@ class WhydBridge extends BridgeAbstract {
if(strlen(preg_replace('/[^0-9a-f]/', '', $this->getInput('u'))) == 24) {
// is input the userid ?
$html = getSimpleHTMLDOM(
- self::URI . 'u/' . preg_replace('/[^0-9a-f]/', '', $this->getInput('u'))
+ self::URI . '/u/' . preg_replace('/[^0-9a-f]/', '', $this->getInput('u'))
) or returnServerError('No results for this query.');
} else { // input may be the username
$html = getSimpleHTMLDOM(
- self::URI . 'search?q=' . urlencode($this->getInput('u'))
+ self::URI . '/search?q=' . urlencode($this->getInput('u'))
) or returnServerError('No results for this query.');
for($j = 0; $j < 5; $j++) {
@@ -57,6 +56,6 @@ class WhydBridge extends BridgeAbstract {
}
public function getName(){
- return (!empty($this->userName) ? $this->userName . ' - ' : '') . 'Whyd Bridge';
+ return (!empty($this->userName) ? $this->userName . ' - ' : '') . 'Openwhyd Bridge';
}
}
diff --git a/bridges/ParuVenduImmoBridge.php b/bridges/ParuVenduImmoBridge.php
index a2e2b33..7b2825b 100644
--- a/bridges/ParuVenduImmoBridge.php
+++ b/bridges/ParuVenduImmoBridge.php
@@ -3,7 +3,7 @@ class ParuVenduImmoBridge extends BridgeAbstract {
const MAINTAINER = 'polo2ro';
const NAME = 'Paru Vendu Immobilier';
- const URI = 'http://www.paruvendu.fr';
+ const URI = 'https://www.paruvendu.fr';
const CACHE_TIMEOUT = 10800; // 3h
const DESCRIPTION = 'Returns the ads from the first page of search result.';
diff --git a/bridges/PickyWallpapersBridge.php b/bridges/PickyWallpapersBridge.php
index 6c26df7..488b448 100644
--- a/bridges/PickyWallpapersBridge.php
+++ b/bridges/PickyWallpapersBridge.php
@@ -3,7 +3,7 @@ class PickyWallpapersBridge extends BridgeAbstract {
const MAINTAINER = 'nel50n';
const NAME = 'PickyWallpapers Bridge';
- const URI = 'http://www.pickywallpapers.com/';
+ const URI = 'https://www.pickywallpapers.com/';
const CACHE_TIMEOUT = 43200; // 12h
const DESCRIPTION = 'Returns the latests wallpapers from PickyWallpapers';
diff --git a/bridges/PikabuBridge.php b/bridges/PikabuBridge.php
index 987070d..a54f6bf 100644
--- a/bridges/PikabuBridge.php
+++ b/bridges/PikabuBridge.php
@@ -110,6 +110,10 @@ class PikabuBridge extends BridgeAbstract {
}
}
$img->outertext = '<img src="' . $src . '">';
+
+ // it is assumed, that img's parents are links to post itself
+ // we don't need them
+ $img->parent()->outertext = $img->outertext;
}
$categories = array();
@@ -125,7 +129,10 @@ class PikabuBridge extends BridgeAbstract {
$item['categories'] = $categories;
$item['author'] = $post->find('.user__nick', 0)->innertext;
$item['title'] = $title->plaintext;
- $item['content'] = strip_tags(backgroundToImg($post->find('.story__content-inner', 0)->innertext), '<br><p><img>');
+ $item['content'] = strip_tags(
+ backgroundToImg($post->find('.story__content-inner', 0)->innertext),
+ '<br><p><img><a>
+ ');
$item['uri'] = $title->href;
$item['timestamp'] = strtotime($time->getAttribute('datetime'));
$this->items[] = $item;
diff --git a/bridges/PinterestBridge.php b/bridges/PinterestBridge.php
index 3e51863..48c0cfc 100644
--- a/bridges/PinterestBridge.php
+++ b/bridges/PinterestBridge.php
@@ -30,7 +30,7 @@ class PinterestBridge extends FeedExpander {
private function fixLowRes() {
- $newitems = [];
+ $newitems = array();
$pattern = '/https\:\/\/i\.pinimg\.com\/[a-zA-Z0-9]*x\//';
foreach($this->items as $item) {
diff --git a/bridges/PlantUMLReleasesBridge.php b/bridges/PlantUMLReleasesBridge.php
new file mode 100644
index 0000000..6648056
--- /dev/null
+++ b/bridges/PlantUMLReleasesBridge.php
@@ -0,0 +1,67 @@
+<?php
+
+/**
+ * PlantUML releases bridge showing latest releases content
+ * @author nicolas-delsaux
+ *
+ */
+class PlantUMLReleasesBridge extends BridgeAbstract
+{
+ const MAINTAINER = 'Riduidel';
+
+ const NAME = 'PlantUML Releases';
+
+ const AUTHOR = 'PlantUML team';
+
+ // URI is no more valid, since we can address the whole gq galaxy
+ const URI = 'http://plantuml.com/fr/changes';
+
+ const CACHE_TIMEOUT = 7200; // 2h
+ const DESCRIPTION = 'PlantUML releases bridge, showing for each release the changelog';
+
+ const DEFAULT_DOMAIN = 'plantuml.com';
+
+ const PARAMETERS = array( array(
+ ));
+
+ const REPLACED_ATTRIBUTES = array(
+ 'href' => 'href',
+ 'src' => 'src',
+ 'data-original' => 'src'
+ );
+
+ private function getDomain() {
+ $domain = $this->getInput('domain');
+ if (empty($domain))
+ $domain = self::DEFAULT_DOMAIN;
+ if (strpos($domain, '://') === false)
+ $domain = 'https://' . $domain;
+ return $domain;
+ }
+
+ public function getURI()
+ {
+ return self::URI;
+ }
+
+ public function collectData()
+ {
+ $html = getSimpleHTMLDOM($this->getURI()) or returnServerError('Could not request ' . $this->getURI());
+
+ // Since GQ don't want simple class scrapping, let's do it the hard way and ... discover content !
+ $main = $html->find('div[id=root]', 0);
+ foreach ($main->find('h2') as $release) {
+ $item = array();
+ $item['author'] = self::AUTHOR;
+ $release_text = $release->innertext;
+ if (preg_match('/(.+) \((.*)\)/', $release_text, $matches)) {
+ $item['title'] = $matches[1];
+ // And now, build the date from the date text
+ $item['timestamp'] = strtotime($matches[2]);
+ }
+ $item['uri'] = $this->getURI();
+ $item['content'] = $release->next_sibling ();
+ $this->items[] = $item;
+ }
+ }
+}
diff --git a/bridges/ReadComicsBridge.php b/bridges/ReadComicsBridge.php
deleted file mode 100644
index 739e6cc..0000000
--- a/bridges/ReadComicsBridge.php
+++ /dev/null
@@ -1,44 +0,0 @@
-<?php
-class ReadComicsBridge extends BridgeAbstract {
-
- const MAINTAINER = 'niawag';
- const NAME = 'Read Comics';
- const URI = 'http://www.readcomics.tv/';
- const DESCRIPTION = 'Enter the comics as they appear in the website uri,
- separated by semicolons, ex: good-comic-1;good-comic-2; ...';
-
- const PARAMETERS = array( array(
- 'q' => array(
- 'name' => 'keywords, separated by semicolons',
- 'exampleValue' => 'first list;second list;...',
- 'required' => true
- ),
- ));
-
- public function collectData(){
-
- function parseDateTimestamp($element){
- $guessedDate = $element->find('span', 0)->plaintext;
- $guessedDate = strptime($guessedDate, '%m/%d/%Y');
- $timestamp = mktime(0, 0, 0, $guessedDate['tm_mon'] + 1, $guessedDate['tm_mday'], date('Y'));
-
- return $timestamp;
- }
-
- $keywordsList = explode(';', $this->getInput('q'));
- foreach($keywordsList as $keywords) {
- $html = $this->getSimpleHTMLDOM(self::URI . 'comic/' . rawurlencode($keywords))
- or $this->returnServerError('Could not request readcomics.tv.');
-
- foreach($html->find('li') as $element) {
- $item = array();
- $item['uri'] = $element->find('a.ch-name', 0)->href;
- $item['id'] = $item['uri'];
- $item['timestamp'] = parseDateTimestamp($element);
- $item['title'] = $element->find('a.ch-name', 0)->plaintext;
- if(isset($item['title']))
- $this->items[] = $item;
- }
- }
- }
-}
diff --git a/bridges/RedditBridge.php b/bridges/RedditBridge.php
new file mode 100644
index 0000000..d83c0a3
--- /dev/null
+++ b/bridges/RedditBridge.php
@@ -0,0 +1,40 @@
+<?php
+class RedditBridge extends FeedExpander {
+
+ const MAINTAINER = 'leomaradan';
+ const NAME = 'Reddit Bridge';
+ const URI = 'https://www.reddit.com/';
+ const DESCRIPTION = 'Reddit RSS Feed fixer';
+
+ const PARAMETERS = array(
+ 'single' => array(
+ 'r' => array(
+ 'name' => 'SubReddit',
+ 'required' => true,
+ 'exampleValue' => 'selfhosted',
+ 'title' => 'SubReddit name'
+ )
+ ),
+ 'multi' => array(
+ 'rs' => array(
+ 'name' => 'SubReddits',
+ 'required' => true,
+ 'exampleValue' => 'selfhosted, php',
+ 'title' => 'SubReddit names, separated by commas'
+ )
+ )
+ );
+
+ public function collectData(){
+
+ switch($this->queriedcontext) {
+ case 'single': $subreddits[] = $this->getInput('r'); break;
+ case 'multi': $subreddits = explode(',', $this->getInput('rs')); break;
+ }
+
+ foreach ($subreddits as $subreddit) {
+ $name = trim($subreddit);
+ $this->collectExpandableDatas("https://www.reddit.com/r/$name/.rss");
+ }
+ }
+}
diff --git a/bridges/Releases3DSBridge.php b/bridges/Releases3DSBridge.php
index 6c159d1..fe2df8e 100644
--- a/bridges/Releases3DSBridge.php
+++ b/bridges/Releases3DSBridge.php
@@ -9,22 +9,6 @@ class Releases3DSBridge extends BridgeAbstract {
public function collectData(){
- function typeToString($type){
- switch($type) {
- case 1: return '3DS Game';
- case 4: return 'eShop';
- default: return '??? (' . $type . ')';
- }
- }
-
- function cardToString($card){
- switch($card) {
- case 1: return 'Regular (CARD1)';
- case 2: return 'NAND (CARD2)';
- default: return '??? (' . $card . ')';
- }
- }
-
$dataUrl = self::URI . 'xml.php';
$xml = getContents($dataUrl)
or returnServerError('Could not request 3dsdb: ' . $dataUrl);
@@ -95,8 +79,8 @@ class Releases3DSBridge extends BridgeAbstract {
. '<br /><b>Release Name: </b>' . $releasename
. '<br /><b>Trimmed size: </b>' . intval(intval($trimmedsize) / 1048576)
. 'MB<br /><b>Firmware: </b>' . $firmware
- . '<br /><b>Type: </b>' . typeToString($type)
- . '<br /><b>Card: </b>' . cardToString($card)
+ . '<br /><b>Type: </b>' . $this->typeToString($type)
+ . '<br /><b>Card: </b>' . $this->cardToString($card)
. '<br />';
//Build search links section to facilitate release search using search engines
@@ -124,4 +108,20 @@ class Releases3DSBridge extends BridgeAbstract {
$limit++;
}
}
+
+ private function typeToString($type){
+ switch($type) {
+ case 1: return '3DS Game';
+ case 4: return 'eShop';
+ default: return '??? (' . $type . ')';
+ }
+ }
+
+ private function cardToString($card){
+ switch($card) {
+ case 1: return 'Regular (CARD1)';
+ case 2: return 'NAND (CARD2)';
+ default: return '??? (' . $card . ')';
+ }
+ }
}
diff --git a/bridges/ReporterreBridge.php b/bridges/ReporterreBridge.php
index 438c55b..41f0f70 100644
--- a/bridges/ReporterreBridge.php
+++ b/bridges/ReporterreBridge.php
@@ -3,7 +3,7 @@ class ReporterreBridge extends BridgeAbstract {
const MAINTAINER = 'nyutag';
const NAME = 'Reporterre Bridge';
- const URI = 'http://www.reporterre.net/';
+ const URI = 'https://www.reporterre.net/';
const DESCRIPTION = 'Returns the newest articles.';
private function extractContent($url){
diff --git a/bridges/RevolutBridge.php b/bridges/RevolutBridge.php
new file mode 100644
index 0000000..04ca377
--- /dev/null
+++ b/bridges/RevolutBridge.php
@@ -0,0 +1,81 @@
+<?php
+
+class RevolutBridge extends BridgeAbstract {
+
+ const NAME = 'Revolut Blog';
+ const URI = 'https://blog.revolut.com/';
+ const DESCRIPTION = 'Returns recent blog posts from Revolut.';
+ const MAINTAINER = 'dominik-th';
+
+ public function getIcon() {
+ return self::URI . 'favicon.png';
+ }
+
+ public function collectData() {
+ $articleOverview = getSimpleHTMLDOM(self::URI . 'sitemap-posts.xml')
+ or returnServerError('Error while downloading the website content');
+
+ $articles = array_slice($articleOverview->find('url'), 0, 15);
+
+ foreach($articles as $article) {
+ $item = array();
+
+ $item['uri'] = $article->find('loc', 0)->plaintext;
+ $item['timestamp'] = $article->find('lastmod', 0)->plaintext;
+ $item['enclosures'] = array(
+ $article->find('image:loc', 0)->plaintext
+ );
+
+ $fullArticle = getSimpleHTMLDOMCached($item['uri'])
+ or returnServerError('Error while downloading the full article');
+
+ $item['author'] = $fullArticle
+ ->find('h4[class="author-card-name"] a', 0)
+ ->plaintext;
+ $item['title'] = $fullArticle
+ ->find('h1[class="post-full-title"]', 0)
+ ->plaintext;
+
+ $content = $fullArticle
+ ->find('section[class="post-full-content"]', 0);
+
+ foreach($content->find('img') as $image) {
+ $image->src = $this->generateAbsoluteUrl($image->src);
+ }
+
+ foreach($content->find('a') as $hyperlink) {
+ $hyperlink->href = $this->generateAbsoluteUrl($hyperlink->href);
+ }
+
+ foreach($content->find('iframe') as $iframe) {
+ $iframe->outertext = $this->generateYoutubeReplacement($iframe);
+ }
+
+ $item['content'] = $content->innertext;
+ $this->items[] = $item;
+ }
+ }
+
+ private function generateAbsoluteUrl($path) {
+ if (filter_var($path, FILTER_VALIDATE_URL)) {
+ return $path;
+ } else {
+ return self::URI . $path;
+ }
+ }
+
+ private function generateYoutubeReplacement($iframe) {
+ $embedUrl = $iframe->src;
+ if (parse_url($embedUrl, PHP_URL_HOST) === 'www.youtube.com') {
+ $urlParts = explode('/', parse_url($embedUrl, PHP_URL_PATH));
+ $videoId = end($urlParts);
+ $thumbnailUrl = 'https://img.youtube.com/vi/' . $videoId . '/0.jpg';
+ $videoUrl = 'https://www.youtube.com/watch?v=' . $videoId;
+ $videoReplacement = str_get_html('<a><img /></a>');
+ $videoReplacement->find('a', 0)->href = $videoUrl;
+ $videoReplacement->find('img', 0)->src = $thumbnailUrl;
+ return $videoReplacement;
+ }
+ return $iframe->outertext;
+ }
+}
diff --git a/bridges/RoadAndTrackBridge.php b/bridges/RoadAndTrackBridge.php
index b3f0acc..22ec8b5 100644
--- a/bridges/RoadAndTrackBridge.php
+++ b/bridges/RoadAndTrackBridge.php
@@ -25,7 +25,7 @@ class RoadAndTrackBridge extends BridgeAbstract {
private function fixImages($content) {
- $enclosures = [];
+ $enclosures = array();
foreach($content->find('img') as $image) {
$image->src = explode('?', $image->getAttribute('data-src'))[0];
$enclosures[] = $image->src;
diff --git a/bridges/Rule34Bridge.php b/bridges/Rule34Bridge.php
index b46ec00..71f48c6 100644
--- a/bridges/Rule34Bridge.php
+++ b/bridges/Rule34Bridge.php
@@ -5,7 +5,7 @@ class Rule34Bridge extends GelbooruBridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Rule34';
- const URI = 'http://rule34.xxx/';
+ const URI = 'https://rule34.xxx/';
const DESCRIPTION = 'Returns images from given page';
const PIDBYPAGE = 50;
diff --git a/bridges/Rule34pahealBridge.php b/bridges/Rule34pahealBridge.php
index d130d36..0e13ed0 100644
--- a/bridges/Rule34pahealBridge.php
+++ b/bridges/Rule34pahealBridge.php
@@ -5,7 +5,7 @@ class Rule34pahealBridge extends Shimmie2Bridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Rule34paheal';
- const URI = 'http://rule34.paheal.net/';
+ const URI = 'https://rule34.paheal.net/';
const DESCRIPTION = 'Returns images from given page';
protected function getItemFromElement($element){
diff --git a/bridges/SafebooruBridge.php b/bridges/SafebooruBridge.php
index d95e557..98da692 100644
--- a/bridges/SafebooruBridge.php
+++ b/bridges/SafebooruBridge.php
@@ -5,7 +5,7 @@ class SafebooruBridge extends GelbooruBridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Safebooru';
- const URI = 'http://safebooru.org/';
+ const URI = 'https://safebooru.org/';
const DESCRIPTION = 'Returns images from given page';
const PIDBYPAGE = 40;
diff --git a/bridges/ScmbBridge.php b/bridges/ScmbBridge.php
index 2107aa3..e8d7f51 100644
--- a/bridges/ScmbBridge.php
+++ b/bridges/ScmbBridge.php
@@ -3,7 +3,7 @@ class ScmbBridge extends BridgeAbstract {
const MAINTAINER = 'Astalaseven';
const NAME = 'Se Coucher Moins Bête Bridge';
- const URI = 'http://secouchermoinsbete.fr';
+ const URI = 'https://secouchermoinsbete.fr';
const CACHE_TIMEOUT = 21600; // 6h
const DESCRIPTION = 'Returns the newest anecdotes.';
diff --git a/bridges/ScoopItBridge.php b/bridges/ScoopItBridge.php
index 997837d..ba586fa 100644
--- a/bridges/ScoopItBridge.php
+++ b/bridges/ScoopItBridge.php
@@ -3,7 +3,7 @@ class ScoopItBridge extends BridgeAbstract {
const MAINTAINER = 'Pitchoule';
const NAME = 'ScoopIt';
- const URI = 'http://www.scoop.it/';
+ const URI = 'https://www.scoop.it/';
const CACHE_TIMEOUT = 21600; // 6h
const DESCRIPTION = 'Returns most recent results from ScoopIt.';
diff --git a/bridges/Shimmie2Bridge.php b/bridges/Shimmie2Bridge.php
index 9923514..fdc97f4 100644
--- a/bridges/Shimmie2Bridge.php
+++ b/bridges/Shimmie2Bridge.php
@@ -4,7 +4,7 @@ require_once('DanbooruBridge.php');
class Shimmie2Bridge extends DanbooruBridge {
const NAME = 'Shimmie v2';
- const URI = 'http://shimmie.shishnet.org/v2/';
+ const URI = 'https://shimmie.shishnet.org/v2/';
const DESCRIPTION = 'Returns images from given page';
const PATHTODATA = '.shm-thumb-link';
diff --git a/bridges/SoundcloudBridge.php b/bridges/SoundcloudBridge.php
index 8938ff9..9607d33 100644
--- a/bridges/SoundcloudBridge.php
+++ b/bridges/SoundcloudBridge.php
@@ -1,7 +1,7 @@
<?php
class SoundCloudBridge extends BridgeAbstract {
- const MAINTAINER = 'kranack';
+ const MAINTAINER = 'kranack, Roliga';
const NAME = 'Soundcloud Bridge';
const URI = 'https://soundcloud.com/';
const CACHE_TIMEOUT = 600; // 10min
@@ -14,27 +14,18 @@ class SoundCloudBridge extends BridgeAbstract {
)
));
- const CLIENT_ID = 'W0KEWWILAjDiRH89X0jpwzuq6rbSK08R';
-
private $feedIcon = null;
+ private $clientIDCache = null;
public function collectData(){
-
- $res = json_decode(getContents(
- 'https://api.soundcloud.com/resolve?url=http://www.soundcloud.com/'
- . urlencode($this->getInput('u'))
- . '&client_id='
- . self::CLIENT_ID
+ $res = $this->apiGet('resolve', array(
+ 'url' => 'http://www.soundcloud.com/' . $this->getInput('u')
)) or returnServerError('No results for this query');
$this->feedIcon = $res->avatar_url;
- $tracks = json_decode(getContents(
- 'https://api.soundcloud.com/users/'
- . urlencode($res->id)
- . '/tracks?client_id='
- . self::CLIENT_ID
- )) or returnServerError('No results for this user');
+ $tracks = $this->apiGet('users/' . urlencode($res->id) . '/tracks')
+ or returnServerError('No results for this user');
$numTracks = min(count($tracks), 10);
for($i = 0; $i < $numTracks; $i++) {
@@ -45,7 +36,7 @@ class SoundCloudBridge extends BridgeAbstract {
$item['content'] = $tracks[$i]->description;
$item['enclosures'] = array($tracks[$i]->uri
. '/stream?client_id='
- . self::CLIENT_ID);
+ . $this->getClientID());
$item['id'] = self::URI
. urlencode($this->getInput('u'))
@@ -75,4 +66,68 @@ class SoundCloudBridge extends BridgeAbstract {
return parent::getName();
}
+
+ private function initClientIDCache(){
+ if($this->clientIDCache !== null)
+ return;
+
+ $cacheFac = new CacheFactory();
+ $cacheFac->setWorkingDir(PATH_LIB_CACHES);
+ $this->clientIDCache = $cacheFac->create(Configuration::getConfig('cache', 'type'));
+ $this->clientIDCache->setScope(get_called_class());
+ $this->clientIDCache->setKey(array('client_id'));
+ }
+
+ private function getClientID(){
+ $this->initClientIDCache();
+
+ $clientID = $this->clientIDCache->loadData();
+
+ if($clientID == null) {
+ return $this->refreshClientID();
+ } else {
+ return $clientID;
+ }
+ }
+
+ private function refreshClientID(){
+ $this->initClientIDCache();
+
+ // Without url=http, this returns a 404
+ $playerHTML = getContents('https://w.soundcloud.com/player/?url=http')
+ or returnServerError('Unable to get player page.');
+ $regex = '/widget-.+?\.js/';
+ if(preg_match($regex, $playerHTML, $matches) == false)
+ returnServerError('Unable to find widget JS URL.');
+ $widgetURL = 'https://widget.sndcdn.com/' . $matches[0];
+
+ $widgetJS = getContents($widgetURL)
+ or returnServerError('Unable to get widget JS page.');
+ $regex = '/client_id.*?"(.+?)"/';
+ if(preg_match($regex, $widgetJS, $matches) == false)
+ returnServerError('Unable to find client ID.');
+ $clientID = $matches[1];
+
+ $this->clientIDCache->saveData($clientID);
+ return $clientID;
+ }
+
+ private function buildAPIURL($endpoint, $parameters){
+ return 'https://api.soundcloud.com/'
+ . $endpoint
+ . '?'
+ . http_build_query($parameters);
+ }
+
+ private function apiGet($endpoint, $parameters = array()){
+ $parameters['client_id'] = $this->getClientID();
+
+ try {
+ return json_decode(getContents($this->buildAPIURL($endpoint, $parameters)));
+ } catch (Exception $e) {
+ // Retry once with refreshed client ID
+ $parameters['client_id'] = $this->refreshClientID();
+ return json_decode(getContents($this->buildAPIURL($endpoint, $parameters)));
+ }
+ }
}
diff --git a/bridges/StoriesIGBridge.php b/bridges/StoriesIGBridge.php
index ddf9846..9b5f7cb 100644
--- a/bridges/StoriesIGBridge.php
+++ b/bridges/StoriesIGBridge.php
@@ -29,6 +29,7 @@ class StoriesIGBridge extends BridgeAbstract {
$item['title'] = $this->getInput('username') . ' story';
$item['uri'] = $result->find('div.download', 0)->find('a', 0)->href;
$item['author'] = $this->getInput('username');
+ $item['timestamp'] = strtotime($result->find('time', 0)->datetime);
$item['uid'] = $result->find('time', 0)->datetime;
$item['content'] = $result;
@@ -44,4 +45,13 @@ class StoriesIGBridge extends BridgeAbstract {
return parent::getURI();
}
+
+ public function getName() {
+
+ if (!is_null($this->getInput('username'))) {
+ return $this->getInput('username') . ' - ' . self::NAME;
+ }
+
+ return parent::getName();
+ }
}
diff --git a/bridges/SuperbWallpapersBridge.php b/bridges/SuperbWallpapersBridge.php
deleted file mode 100644
index 610dd32..0000000
--- a/bridges/SuperbWallpapersBridge.php
+++ /dev/null
@@ -1,70 +0,0 @@
-<?php
-class SuperbWallpapersBridge extends BridgeAbstract {
-
- const MAINTAINER = 'nel50n';
- const NAME = 'Superb Wallpapers Bridge';
- const URI = 'http://www.superbwallpapers.com/';
- const CACHE_TIMEOUT = 43200; // 12h
- const DESCRIPTION = 'Returns the latests wallpapers from SuperbWallpapers';
-
- const PARAMETERS = array( array(
- 'c' => array(
- 'name' => 'category',
- 'required' => true
- ),
- 'm' => array(
- 'name' => 'Max number of wallpapers',
- 'type' => 'number'
- ),
- 'r' => array(
- 'name' => 'resolution',
- 'exampleValue' => '1920x1200, 1680x1050,…',
- 'defaultValue' => '1920x1200'
- )
- ));
-
- public function collectData(){
- $category = $this->getInput('c');
- $resolution = $this->getInput('r'); // Wide wallpaper default
-
- $num = 0;
- $max = $this->getInput('m') ?: 36;
- $lastpage = 1;
-
- // Get last page number
- $link = self::URI . '/' . $category . '/9999.html';
- $html = getSimpleHTMLDOM($link)
- or returnServerError('Could not load ' . $link);
-
- $lastpage = min($html->find('.paging .cpage', 0)->innertext(), ceil($max / 36));
-
- for($page = 1; $page <= $lastpage; $page++) {
- $link = self::URI . '/' . $category . '/' . $page . '.html';
- $html = getSimpleHTMLDOM($link)
- or returnServerError('No results for this query.');
-
- foreach($html->find('.wpl .i a') as $element) {
- $thumbnail = $element->find('img', 0);
-
- $item = array();
- $item['uri'] = str_replace('200x125', $this->resolution, $thumbnail->src);
- $item['timestamp'] = time();
- $item['title'] = $element->title;
- $item['content'] = $item['title'] . '<br><a href="' . $item['uri'] . '">' . $thumbnail . '</a>';
- $this->items[] = $item;
-
- $num++;
- if ($num >= $max)
- break 2;
- }
- }
- }
-
- public function getName(){
- if(!is_null($this->getInput('c')) && !is_null($this->getInput('r'))) {
- return self::NAME . '- ' . $this->getInput('c') . ' [' . $this->getInput('r') . ']';
- }
-
- return parent::getName();
- }
-}
diff --git a/bridges/TbibBridge.php b/bridges/TbibBridge.php
index edb761e..819d61e 100644
--- a/bridges/TbibBridge.php
+++ b/bridges/TbibBridge.php
@@ -5,7 +5,7 @@ class TbibBridge extends GelbooruBridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Tbib';
- const URI = 'http://tbib.org/';
+ const URI = 'https://tbib.org/';
const DESCRIPTION = 'Returns images from given page';
const PIDBYPAGE = 50;
diff --git a/bridges/TheCodingLoveBridge.php b/bridges/TheCodingLoveBridge.php
index 2a639e3..8060c94 100644
--- a/bridges/TheCodingLoveBridge.php
+++ b/bridges/TheCodingLoveBridge.php
@@ -3,7 +3,7 @@ class TheCodingLoveBridge extends BridgeAbstract {
const MAINTAINER = 'superbaillot.net';
const NAME = 'The Coding Love';
- const URI = 'http://thecodinglove.com/';
+ const URI = 'https://thecodinglove.com/';
const CACHE_TIMEOUT = 7200; // 2h
const DESCRIPTION = 'The Coding Love';
diff --git a/bridges/ThePirateBayBridge.php b/bridges/ThePirateBayBridge.php
index 5fc04eb..4b45daf 100644
--- a/bridges/ThePirateBayBridge.php
+++ b/bridges/ThePirateBayBridge.php
@@ -40,60 +40,6 @@ class ThePirateBayBridge extends BridgeAbstract {
public function collectData(){
- function parseDateTimestamp($element){
- $guessedDate = $element->find('font', 0)->plaintext;
- $guessedDate = explode('Uploaded ', $guessedDate)[1];
- $guessedDate = explode(',', $guessedDate)[0];
-
- if(count(explode(':', $guessedDate)) == 1) {
- $guessedDate = strptime($guessedDate, '%m-%d&nbsp;%Y');
- $timestamp = mktime(
- 0,
- 0,
- 0,
- $guessedDate['tm_mon'] + 1,
- $guessedDate['tm_mday'],
- 1900 + $guessedDate['tm_year']
- );
- } elseif(explode('&nbsp;', $guessedDate)[0] == 'Today') {
- $guessedDate = strptime(
- explode('&nbsp;', $guessedDate)[1], '%H:%M'
- );
-
- $timestamp = mktime(
- $guessedDate['tm_hour'],
- $guessedDate['tm_min'],
- 0,
- date('m'),
- date('d'),
- date('Y')
- );
- } elseif(explode('&nbsp;', $guessedDate)[0] == 'Y-day') {
- $guessedDate = strptime(
- explode('&nbsp;', $guessedDate)[1], '%H:%M'
- );
-
- $timestamp = mktime(
- $guessedDate['tm_hour'],
- $guessedDate['tm_min'],
- 0,
- date('m', time() - 24 * 60 * 60),
- date('d', time() - 24 * 60 * 60),
- date('Y', time() - 24 * 60 * 60)
- );
- } else {
- $guessedDate = strptime($guessedDate, '%m-%d&nbsp;%H:%M');
- $timestamp = mktime(
- $guessedDate['tm_hour'],
- $guessedDate['tm_min'],
- 0,
- $guessedDate['tm_mon'] + 1,
- $guessedDate['tm_mday'],
- date('Y'));
- }
- return $timestamp;
- }
-
$catBool = $this->getInput('catCheck');
if($catBool) {
$catNum = $this->getInput('cat');
@@ -151,7 +97,7 @@ class ThePirateBayBridge extends BridgeAbstract {
$item = array();
$item['uri'] = self::URI . $element->find('a.detLink', 0)->href;
$item['id'] = self::URI . $element->find('a.detLink', 0)->href;
- $item['timestamp'] = parseDateTimestamp($element);
+ $item['timestamp'] = $this->parseDateTimestamp($element);
$item['author'] = $element->find('a.detDesc', 0)->plaintext;
$item['title'] = $element->find('a.detLink', 0)->plaintext;
$item['magnet'] = $element->find('a', 3)->href;
@@ -174,4 +120,58 @@ class ThePirateBayBridge extends BridgeAbstract {
}
}
}
+
+ private function parseDateTimestamp($element){
+ $guessedDate = $element->find('font', 0)->plaintext;
+ $guessedDate = explode('Uploaded ', $guessedDate)[1];
+ $guessedDate = explode(',', $guessedDate)[0];
+
+ if(count(explode(':', $guessedDate)) == 1) {
+ $guessedDate = strptime($guessedDate, '%m-%d&nbsp;%Y');
+ $timestamp = mktime(
+ 0,
+ 0,
+ 0,
+ $guessedDate['tm_mon'] + 1,
+ $guessedDate['tm_mday'],
+ 1900 + $guessedDate['tm_year']
+ );
+ } elseif(explode('&nbsp;', $guessedDate)[0] == 'Today') {
+ $guessedDate = strptime(
+ explode('&nbsp;', $guessedDate)[1], '%H:%M'
+ );
+
+ $timestamp = mktime(
+ $guessedDate['tm_hour'],
+ $guessedDate['tm_min'],
+ 0,
+ date('m'),
+ date('d'),
+ date('Y')
+ );
+ } elseif(explode('&nbsp;', $guessedDate)[0] == 'Y-day') {
+ $guessedDate = strptime(
+ explode('&nbsp;', $guessedDate)[1], '%H:%M'
+ );
+
+ $timestamp = mktime(
+ $guessedDate['tm_hour'],
+ $guessedDate['tm_min'],
+ 0,
+ date('m', time() - 24 * 60 * 60),
+ date('d', time() - 24 * 60 * 60),
+ date('Y', time() - 24 * 60 * 60)
+ );
+ } else {
+ $guessedDate = strptime($guessedDate, '%m-%d&nbsp;%H:%M');
+ $timestamp = mktime(
+ $guessedDate['tm_hour'],
+ $guessedDate['tm_min'],
+ 0,
+ $guessedDate['tm_mon'] + 1,
+ $guessedDate['tm_mday'],
+ date('Y'));
+ }
+ return $timestamp;
+ }
}
diff --git a/bridges/TheWhiteboardBridge.php b/bridges/TheWhiteboardBridge.php
new file mode 100644
index 0000000..051d15e
--- /dev/null
+++ b/bridges/TheWhiteboardBridge.php
@@ -0,0 +1,22 @@
+<?php
+class TheWhiteboardBridge extends BridgeAbstract {
+ const NAME = 'The Whiteboard';
+ const URI = 'https://www.the-whiteboard.com/';
+ const DESCRIPTION = 'Get the latest comic from The Whiteboard';
+ const MAINTAINER = 'CyberJacob';
+
+ public function collectData() {
+ $item = array();
+
+ $html = getSimpleHTMLDOM(self::URI) or returnServerError('Could not load The Whiteboard.');
+
+ $image = $html->find('center', 1)->find('img', 0);
+ $image->src = self::URI . '/' . $image->src;
+
+ $item['title'] = explode("\r\n", $html->find('center', 1)->plaintext)[0];
+ $item['content'] = $image;
+ $item['timestamp'] = explode("\r\n", $html->find('center', 1)->plaintext)[0];
+
+ $this->items[] = $item;
+ }
+}
diff --git a/bridges/VarietyBridge.php b/bridges/VarietyBridge.php
new file mode 100644
index 0000000..a2e6170
--- /dev/null
+++ b/bridges/VarietyBridge.php
@@ -0,0 +1,30 @@
+<?php
+class VarietyBridge extends FeedExpander {
+
+ const MAINTAINER = 'IceWreck';
+ const NAME = 'Variety Bridge';
+ const URI = 'https://variety.com';
+ const CACHE_TIMEOUT = 3600;
+ const DESCRIPTION = 'RSS feed for Variety';
+
+ public function collectData(){
+ $this->collectExpandableDatas('http://feeds.feedburner.com/variety/headlines', 15);
+ }
+
+ protected function parseItem($newsItem){
+ $item = parent::parseItem($newsItem);
+ // $articlePage gets the entire page's contents
+ $articlePage = getSimpleHTMLDOM($newsItem->link);
+
+ // Remove Script tags
+ foreach($articlePage->find('script') as $script_tag) {
+ $script_tag->remove();
+ }
+ $article = $articlePage->find('div.c-featured-media', 0);
+ $article = $article . $articlePage->find('.c-content', 0);
+
+ $item['content'] = $article;
+
+ return $item;
+ }
+}
diff --git a/bridges/ViceBridge.php b/bridges/ViceBridge.php
new file mode 100644
index 0000000..4dccb8e
--- /dev/null
+++ b/bridges/ViceBridge.php
@@ -0,0 +1,38 @@
+<?php
+class ViceBridge extends FeedExpander {
+ const MAINTAINER = 'IceWreck';
+ const NAME = 'Vice Bridge';
+ const URI = 'https://www.vice.com/';
+ const CACHE_TIMEOUT = 3600; // This is a news site, so don't cache for more than 10 mins
+ const DESCRIPTION = 'RSS feed for vice publications like Vice News, Munchies, Motherboard, etc.';
+ const PARAMETERS = array( array(
+ 'feed' => array(
+ 'name' => 'Feed',
+ 'type' => 'list',
+ 'values' => array(
+ 'Vice News' => 'rss',
+ 'Motherboard - Tech' => 'en_us/rss/topic/tech',
+ 'Entertainment' => 'en_us/rss/topic/entertainment',
+ 'Noisey - Music' => 'en_us/rss/topic/music',
+ 'Munchies - Food' => 'en_us/rss/topic/food'
+ )
+ )
+ ));
+
+ public function collectData(){
+ $feed = $this->getInput('feed');
+ $feedURL = 'https://www.vice.com/' . $feed;
+ $this->collectExpandableDatas($feedURL, 10);
+ }
+
+ protected function parseItem($newsItem){
+ $item = parent::parseItem($newsItem);
+ // $articlePage gets the entire page's contents
+ $articlePage = getSimpleHTMLDOM($newsItem->link);
+ // text and embedded content
+ $article = $article . $articlePage->find('.article__body', 0);
+ $item['content'] = $article;
+
+ return $item;
+ }
+}
diff --git a/bridges/VieDeMerdeBridge.php b/bridges/VieDeMerdeBridge.php
new file mode 100644
index 0000000..1224798
--- /dev/null
+++ b/bridges/VieDeMerdeBridge.php
@@ -0,0 +1,56 @@
+<?php
+class VieDeMerdeBridge extends BridgeAbstract {
+
+ const MAINTAINER = 'floviolleau';
+ const NAME = 'VieDeMerde Bridge';
+ const URI = 'https://viedemerde.fr';
+ const DESCRIPTION = 'Returns latest quotes from VieDeMerde.';
+ const CACHE_TIMEOUT = 7200;
+
+ const PARAMETERS = array(array(
+ 'item_limit' => array(
+ 'name' => 'Limit number of returned items',
+ 'type' => 'number',
+ 'defaultValue' => 20
+ )
+ ));
+
+ public function collectData() {
+ $limit = $this->getInput('item_limit');
+
+ if ($limit < 1) {
+ $limit = 20;
+ }
+
+ $html = getSimpleHTMLDOM(self::URI, array())
+ or returnServerError('Could not request VieDeMerde.');
+
+ $quotes = $html->find('article.article-panel');
+ if(sizeof($quotes) === 0) {
+ return;
+ }
+
+ foreach($quotes as $quote) {
+ $item = array();
+ $item['uri'] = self::URI . $quote->find('.article-contents a', 0)->href;
+ $titleContent = $quote->find('.article-contents a h2.classic-title', 0);
+
+ if($titleContent) {
+ $item['title'] = html_entity_decode($titleContent->plaintext, ENT_QUOTES);
+ } else {
+ continue;
+ }
+
+ $quote->find('.article-contents a h2.classic-title', 0)->outertext = '';
+ $item['content'] = $quote->find('.article-contents a', 0)->innertext;
+ $item['author'] = $quote->find('.article-topbar', 0)->innertext;
+ $item['uid'] = hash('sha256', $item['title']);
+
+ $this->items[] = $item;
+
+ if (count($this->items) >= $limit) {
+ break;
+ }
+ }
+ }
+}
diff --git a/bridges/VkBridge.php b/bridges/VkBridge.php
index f9aaa66..713b86f 100644
--- a/bridges/VkBridge.php
+++ b/bridges/VkBridge.php
@@ -3,7 +3,9 @@
class VkBridge extends BridgeAbstract
{
- const MAINTAINER = 'ahiles3005';
+ const MAINTAINER = 'em92';
+ // const MAINTAINER = 'pmaziere';
+ // const MAINTAINER = 'ahiles3005';
const NAME = 'VK.com';
const URI = 'https://vk.com/';
const CACHE_TIMEOUT = 300; // 5min
@@ -26,7 +28,7 @@ class VkBridge extends BridgeAbstract
protected function getAccessToken()
{
- return 'c8071613517c155c6cfbd2a059b2718e9c37b89094c4766834969dda75f657a2c1cbb49bab4c5e649f1db';
+ return 'e69b2db9f6cd4a97c0716893232587165c18be85bc1af1834560125c1d3c8ec281eb407a78cca0ae16776';
}
public function getURI()
@@ -165,7 +167,7 @@ class VkBridge extends BridgeAbstract
}
// get all photos
- foreach($post->find('div.wall_text > a.page_post_thumb_wrap') as $a) {
+ foreach($post->find('div.wall_text a.page_post_thumb_wrap') as $a) {
$result = $this->getPhoto($a);
if ($result == null) continue;
$a->outertext = '';
@@ -237,6 +239,41 @@ class VkBridge extends BridgeAbstract
$a->outertext = '';
}
+ // fix links and get post hashtags
+ $hashtags = array();
+ foreach($post->find('a') as $a) {
+ $href = $a->getAttribute('href');
+ $innertext = $a->innertext;
+
+ $hashtag_prefix = '/feed?section=search&q=%23';
+ $hashtag = null;
+
+ if ($href && substr($href, 0, strlen($hashtag_prefix)) === $hashtag_prefix) {
+ $hashtag = urldecode(substr($href, strlen($hashtag_prefix)));
+ } else if (substr($innertext, 0, 1) == '#') {
+ $hashtag = $innertext;
+ }
+
+ if ($hashtag) {
+ $a->outertext = $innertext;
+ $hashtags[] = $hashtag;
+ continue;
+ }
+
+ $parsed_url = parse_url($href);
+
+ if (array_key_exists('path', $parsed_url) === false) continue;
+
+ if (strpos($parsed_url['path'], '/away.php') === 0) {
+ parse_str($parsed_url['query'], $parsed_query);
+ $a->setAttribute('href', iconv(
+ 'windows-1251',
+ 'utf-8//ignore',
+ $parsed_query['to']
+ ));
+ }
+ }
+
if (is_object($post->find('div.copy_quote', 0))) {
if ($this->getInput('hide_reposts') === true) {
continue;
@@ -250,21 +287,9 @@ class VkBridge extends BridgeAbstract
}
$item = array();
- $item['content'] = strip_tags(backgroundToImg($post->find('div.wall_text', 0)->innertext), '<br><img>');
+ $item['content'] = strip_tags(backgroundToImg($post->find('div.wall_text', 0)->innertext), '<a><br><img>');
$item['content'] .= $content_suffix;
- $item['categories'] = array();
-
- // get post hashtags
- foreach($post->find('a') as $a) {
- $href = $a->getAttribute('href');
- $prefix = '/feed?section=search&q=%23';
- $innertext = $a->innertext;
- if ($href && substr($href, 0, strlen($prefix)) === $prefix) {
- $item['categories'][] = urldecode(substr($href, strlen($prefix)));
- } else if (substr($innertext, 0, 1) == '#') {
- $item['categories'][] = $innertext;
- }
- }
+ $item['categories'] = $hashtags;
// get post link
$post_link = $post->find('a.post_link', 0)->getAttribute('href');
@@ -354,6 +379,8 @@ class VkBridge extends BridgeAbstract
}
$date = date_parse($strdate);
+ } elseif ($date['hour'] === false) {
+ $date['hour'] = $date['minute'] = '00';
}
return strtotime($date['day'] . '-' . $date['month'] . '-' . $date['year'] . ' ' .
$date['hour'] . ':' . $date['minute']);
diff --git a/bridges/XbooruBridge.php b/bridges/XbooruBridge.php
index d3605be..2b0f2e3 100644
--- a/bridges/XbooruBridge.php
+++ b/bridges/XbooruBridge.php
@@ -5,7 +5,7 @@ class XbooruBridge extends GelbooruBridge {
const MAINTAINER = 'mitsukarenai';
const NAME = 'Xbooru';
- const URI = 'http://xbooru.com/';
+ const URI = 'https://xbooru.com/';
const DESCRIPTION = 'Returns images from given page';
const PIDBYPAGE = 50;
diff --git a/bridges/XenForoBridge.php b/bridges/XenForoBridge.php
index 983654e..7e210ee 100644
--- a/bridges/XenForoBridge.php
+++ b/bridges/XenForoBridge.php
@@ -395,7 +395,7 @@ class XenForoBridge extends BridgeAbstract {
*/
private function fixDate($date, $lang = 'en-US') {
- $mnamesen = [
+ $mnamesen = array(
'January',
'Feburary',
'March',
@@ -408,7 +408,7 @@ class XenForoBridge extends BridgeAbstract {
'October',
'November',
'December'
- ];
+ );
switch($lang) {
case 'en-US': // example: Jun 9, 2018 at 11:46 PM
@@ -418,7 +418,7 @@ class XenForoBridge extends BridgeAbstract {
case 'de-DE': // example: 19 Juli 2018 um 19:27 Uhr
- $mnamesde = [
+ $mnamesde = array(
'Januar',
'Februar',
'März',
@@ -431,9 +431,9 @@ class XenForoBridge extends BridgeAbstract {
'Oktober',
'November',
'Dezember'
- ];
+ );
- $mnamesdeshort = [
+ $mnamesdeshort = array(
'Jan.',
'Feb.',
'Mär.',
@@ -446,7 +446,7 @@ class XenForoBridge extends BridgeAbstract {
'Okt.',
'Nov.',
'Dez.'
- ];
+ );
$date = str_ireplace($mnamesde, $mnamesen, $date);
$date = str_ireplace($mnamesdeshort, $mnamesen, $date);
diff --git a/bridges/YahtzeeDevDiaryBridge.php b/bridges/YahtzeeDevDiaryBridge.php
new file mode 100644
index 0000000..3e3b2b0
--- /dev/null
+++ b/bridges/YahtzeeDevDiaryBridge.php
@@ -0,0 +1,21 @@
+<?php
+class YahtzeeDevDiaryBridge extends BridgeAbstract {
+ const MAINTAINER = 'somini';
+ const NAME = "Yahtzee's Dev Diary";
+ const URI = 'https://www.escapistmagazine.com/v2/yahtzees-dev-diary-completed-games-list/';
+ const DESCRIPTION = 'Yahtzee’s Dev Diary Series';
+
+ public function collectData(){
+ $html = getSimpleHTMLDOM($this->getURI())
+ or returnServerError('Could not load content');
+
+ foreach($html->find('blockquote.wp-embedded-content a') as $element) {
+ $item = array();
+
+ $item['title'] = $element->innertext;
+ $item['uri'] = $element->href;
+
+ $this->items[] = $item;
+ }
+ }
+}
diff --git a/bridges/ZoneTelechargementBridge.php b/bridges/ZoneTelechargementBridge.php
index 44cdfce..ab7b947 100644
--- a/bridges/ZoneTelechargementBridge.php
+++ b/bridges/ZoneTelechargementBridge.php
@@ -7,9 +7,9 @@ class ZoneTelechargementBridge extends BridgeAbstract {
* name of the bridge. This permits to keep the same RSS Feed URL.
*/
- const NAME = 'Annuaire Telechargement';
- const URI = 'https://www.annuaire-telechargement.com/';
- const DESCRIPTION = 'Suivi de série sur Annuaire Telechargement';
+ const NAME = 'Zone Telechargement';
+ const URI = 'https://www.zone-telechargement.net/';
+ const DESCRIPTION = 'Suivi de série sur Zone Telechargement';
const MAINTAINER = 'sysadminstory';
const PARAMETERS = array(
'Suivre la publication des épisodes d\'une série en cours de diffusion' => array(
@@ -17,14 +17,14 @@ class ZoneTelechargementBridge extends BridgeAbstract {
'name' => 'URL de la série',
'type' => 'text',
'required' => true,
- 'title' => 'URL d\'une série sans le https://www.annuaire-telechargement.com/',
+ 'title' => 'URL d\'une série sans le https://wwv.zone-telechargement.net/',
'exampleValue' => 'telecharger-series/31079-halt-and-catch-fire-saison-4-french-hd720p.html'
)
)
);
public function getIcon() {
- return 'https://www.annuaire-telechargement.com/templates/Default/images/favicon.ico';
+ return self::URI . '/templates/Default/images/favicon.ico';
}
public function collectData(){
diff --git a/composer.json b/composer.json
index 8748cb3..3c03eeb 100644
--- a/composer.json
+++ b/composer.json
@@ -1,12 +1,39 @@
{
+ "name": "rss-bridge/rss-bridge",
+ "description": "RSS-Bridge is a PHP project capable of generating RSS and Atom feeds for websites that don't have one. It can be used on webservers or as a stand-alone application in CLI mode.",
+ "keywords": [
+ "php",
+ "rss",
+ "bridge",
+ "rss-bridge",
+ "atom",
+ "html",
+ "json",
+ "feed",
+ "cli"
+ ],
+ "homepage": "https://github.com/rss-bridge/rss-bridge/",
+ "license": "UNLICENSE",
+ "support": {
+ "issues": "https://github.com/rss-bridge/rss-bridge/issues/",
+ "wiki": "https://github.com/rss-bridge/rss-bridge/wiki/",
+ "source": "https://github.com/rss-bridge/rss-bridge/",
+ "rss": "https://github.com/RSS-Bridge/rss-bridge/commits/master.atom"
+ },
"require": {
- "php": ">=5.6",
- "ext-mbstring": "*",
- "ext-sqlite3": "*",
- "ext-curl": "*",
- "ext-openssl": "*",
- "ext-libxml": "*",
- "ext-simplexml": "*",
- "ext-json": "*"
+ "php": ">=5.6",
+ "ext-mbstring": "*",
+ "ext-curl": "*",
+ "ext-openssl": "*",
+ "ext-libxml": "*",
+ "ext-simplexml": "*",
+ "ext-json": "*"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6 || ^7"
+ },
+ "suggest": {
+ "ext-memcached": "Allows to use memcached as cache type",
+ "ext-sqlite3": "Allows to use an SQLite database for caching"
}
}
diff --git a/composer.lock b/composer.lock
index 3d8d9f2..918c430 100644
--- a/composer.lock
+++ b/composer.lock
@@ -4,9 +4,1479 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
- "content-hash": "ef341ee18f28c7bd5832e188fe157734",
+ "content-hash": "b60dc7dd86ffc8be27b94fc71894cad0",
"packages": [],
- "packages-dev": [],
+ "packages-dev": [
+ {
+ "name": "doctrine/instantiator",
+ "version": "1.2.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/doctrine/instantiator.git",
+ "reference": "a2c590166b2133a4633738648b6b064edae0814a"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/doctrine/instantiator/zipball/a2c590166b2133a4633738648b6b064edae0814a",
+ "reference": "a2c590166b2133a4633738648b6b064edae0814a",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "doctrine/coding-standard": "^6.0",
+ "ext-pdo": "*",
+ "ext-phar": "*",
+ "phpbench/phpbench": "^0.13",
+ "phpstan/phpstan-phpunit": "^0.11",
+ "phpstan/phpstan-shim": "^0.11",
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.2.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Doctrine\\Instantiator\\": "src/Doctrine/Instantiator/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Marco Pivetta",
+ "email": "ocramius@gmail.com",
+ "homepage": "http://ocramius.github.com/"
+ }
+ ],
+ "description": "A small, lightweight utility to instantiate objects in PHP without invoking their constructors",
+ "homepage": "https://www.doctrine-project.org/projects/instantiator.html",
+ "keywords": [
+ "constructor",
+ "instantiate"
+ ],
+ "time": "2019-03-17T17:37:11+00:00"
+ },
+ {
+ "name": "myclabs/deep-copy",
+ "version": "1.9.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/myclabs/DeepCopy.git",
+ "reference": "007c053ae6f31bba39dfa19a7726f56e9763bbea"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/myclabs/DeepCopy/zipball/007c053ae6f31bba39dfa19a7726f56e9763bbea",
+ "reference": "007c053ae6f31bba39dfa19a7726f56e9763bbea",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "replace": {
+ "myclabs/deep-copy": "self.version"
+ },
+ "require-dev": {
+ "doctrine/collections": "^1.0",
+ "doctrine/common": "^2.6",
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "DeepCopy\\": "src/DeepCopy/"
+ },
+ "files": [
+ "src/DeepCopy/deep_copy.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "description": "Create deep copies (clones) of your objects",
+ "keywords": [
+ "clone",
+ "copy",
+ "duplicate",
+ "object",
+ "object graph"
+ ],
+ "time": "2019-08-09T12:45:53+00:00"
+ },
+ {
+ "name": "phar-io/manifest",
+ "version": "1.0.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/manifest.git",
+ "reference": "7761fcacf03b4d4f16e7ccb606d4879ca431fcf4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/manifest/zipball/7761fcacf03b4d4f16e7ccb606d4879ca431fcf4",
+ "reference": "7761fcacf03b4d4f16e7ccb606d4879ca431fcf4",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-phar": "*",
+ "phar-io/version": "^2.0",
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Component for reading phar.io manifest information from a PHP Archive (PHAR)",
+ "time": "2018-07-08T19:23:20+00:00"
+ },
+ {
+ "name": "phar-io/version",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phar-io/version.git",
+ "reference": "45a2ec53a73c70ce41d55cedef9063630abaf1b6"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phar-io/version/zipball/45a2ec53a73c70ce41d55cedef9063630abaf1b6",
+ "reference": "45a2ec53a73c70ce41d55cedef9063630abaf1b6",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Heuer",
+ "email": "sebastian@phpeople.de",
+ "role": "Developer"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "Library for handling version information and constraints",
+ "time": "2018-07-08T19:19:57+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-common",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionCommon.git",
+ "reference": "63a995caa1ca9e5590304cd845c15ad6d482a62a"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionCommon/zipball/63a995caa1ca9e5590304cd845c15ad6d482a62a",
+ "reference": "63a995caa1ca9e5590304cd845c15ad6d482a62a",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "~6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Jaap van Otterdijk",
+ "email": "opensource@ijaap.nl"
+ }
+ ],
+ "description": "Common reflection classes used by phpdocumentor to reflect the code structure",
+ "homepage": "http://www.phpdoc.org",
+ "keywords": [
+ "FQSEN",
+ "phpDocumentor",
+ "phpdoc",
+ "reflection",
+ "static analysis"
+ ],
+ "time": "2018-08-07T13:53:10+00:00"
+ },
+ {
+ "name": "phpdocumentor/reflection-docblock",
+ "version": "4.3.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/ReflectionDocBlock.git",
+ "reference": "b83ff7cfcfee7827e1e78b637a5904fe6a96698e"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/ReflectionDocBlock/zipball/b83ff7cfcfee7827e1e78b637a5904fe6a96698e",
+ "reference": "b83ff7cfcfee7827e1e78b637a5904fe6a96698e",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "phpdocumentor/reflection-common": "^1.0.0 || ^2.0.0",
+ "phpdocumentor/type-resolver": "~0.4 || ^1.0.0",
+ "webmozart/assert": "^1.0"
+ },
+ "require-dev": {
+ "doctrine/instantiator": "^1.0.5",
+ "mockery/mockery": "^1.0",
+ "phpunit/phpunit": "^6.4"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": [
+ "src/"
+ ]
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "description": "With this component, a library can provide support for annotations via DocBlocks or otherwise retrieve information that is embedded in a DocBlock.",
+ "time": "2019-09-12T14:27:41+00:00"
+ },
+ {
+ "name": "phpdocumentor/type-resolver",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpDocumentor/TypeResolver.git",
+ "reference": "2e32a6d48972b2c1976ed5d8967145b6cec4a4a9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpDocumentor/TypeResolver/zipball/2e32a6d48972b2c1976ed5d8967145b6cec4a4a9",
+ "reference": "2e32a6d48972b2c1976ed5d8967145b6cec4a4a9",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1",
+ "phpdocumentor/reflection-common": "^2.0"
+ },
+ "require-dev": {
+ "ext-tokenizer": "^7.1",
+ "mockery/mockery": "~1",
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "phpDocumentor\\Reflection\\": "src"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Mike van Riel",
+ "email": "me@mikevanriel.com"
+ }
+ ],
+ "description": "A PSR-5 based resolver of Class names, Types and Structural Element Names",
+ "time": "2019-08-22T18:11:29+00:00"
+ },
+ {
+ "name": "phpspec/prophecy",
+ "version": "1.9.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/phpspec/prophecy.git",
+ "reference": "f6811d96d97bdf400077a0cc100ae56aa32b9203"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/phpspec/prophecy/zipball/f6811d96d97bdf400077a0cc100ae56aa32b9203",
+ "reference": "f6811d96d97bdf400077a0cc100ae56aa32b9203",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.0.2",
+ "php": "^5.3|^7.0",
+ "phpdocumentor/reflection-docblock": "^2.0|^3.0.2|^4.0|^5.0",
+ "sebastian/comparator": "^1.1|^2.0|^3.0",
+ "sebastian/recursion-context": "^1.0|^2.0|^3.0"
+ },
+ "require-dev": {
+ "phpspec/phpspec": "^2.5|^3.2",
+ "phpunit/phpunit": "^4.8.35 || ^5.7 || ^6.5 || ^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.8.x-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Prophecy\\": "src/Prophecy"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Konstantin Kudryashov",
+ "email": "ever.zet@gmail.com",
+ "homepage": "http://everzet.com"
+ },
+ {
+ "name": "Marcello Duarte",
+ "email": "marcello.duarte@gmail.com"
+ }
+ ],
+ "description": "Highly opinionated mocking framework for PHP 5.3+",
+ "homepage": "https://github.com/phpspec/prophecy",
+ "keywords": [
+ "Double",
+ "Dummy",
+ "fake",
+ "mock",
+ "spy",
+ "stub"
+ ],
+ "time": "2019-10-03T11:07:50+00:00"
+ },
+ {
+ "name": "phpunit/php-code-coverage",
+ "version": "6.1.4",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-code-coverage.git",
+ "reference": "807e6013b00af69b6c5d9ceb4282d0393dbb9d8d"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/807e6013b00af69b6c5d9ceb4282d0393dbb9d8d",
+ "reference": "807e6013b00af69b6c5d9ceb4282d0393dbb9d8d",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.1",
+ "phpunit/php-file-iterator": "^2.0",
+ "phpunit/php-text-template": "^1.2.1",
+ "phpunit/php-token-stream": "^3.0",
+ "sebastian/code-unit-reverse-lookup": "^1.0.1",
+ "sebastian/environment": "^3.1 || ^4.0",
+ "sebastian/version": "^2.0.1",
+ "theseer/tokenizer": "^1.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "suggest": {
+ "ext-xdebug": "^2.6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "6.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that provides collection, processing, and rendering functionality for PHP code coverage information.",
+ "homepage": "https://github.com/sebastianbergmann/php-code-coverage",
+ "keywords": [
+ "coverage",
+ "testing",
+ "xunit"
+ ],
+ "time": "2018-10-31T16:06:48+00:00"
+ },
+ {
+ "name": "phpunit/php-file-iterator",
+ "version": "2.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-file-iterator.git",
+ "reference": "050bedf145a257b1ff02746c31894800e5122946"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-file-iterator/zipball/050bedf145a257b1ff02746c31894800e5122946",
+ "reference": "050bedf145a257b1ff02746c31894800e5122946",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "FilterIterator implementation that filters files based on a list of suffixes.",
+ "homepage": "https://github.com/sebastianbergmann/php-file-iterator/",
+ "keywords": [
+ "filesystem",
+ "iterator"
+ ],
+ "time": "2018-09-13T20:33:42+00:00"
+ },
+ {
+ "name": "phpunit/php-text-template",
+ "version": "1.2.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-text-template.git",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-text-template/zipball/31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "reference": "31f8b717e51d9a2afca6c9f046f5d69fc27c8686",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Simple template engine.",
+ "homepage": "https://github.com/sebastianbergmann/php-text-template/",
+ "keywords": [
+ "template"
+ ],
+ "time": "2015-06-21T13:50:34+00:00"
+ },
+ {
+ "name": "phpunit/php-timer",
+ "version": "2.1.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-timer.git",
+ "reference": "1038454804406b0b5f5f520358e78c1c2f71501e"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-timer/zipball/1038454804406b0b5f5f520358e78c1c2f71501e",
+ "reference": "1038454804406b0b5f5f520358e78c1c2f71501e",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Utility class for timing",
+ "homepage": "https://github.com/sebastianbergmann/php-timer/",
+ "keywords": [
+ "timer"
+ ],
+ "time": "2019-06-07T04:22:29+00:00"
+ },
+ {
+ "name": "phpunit/php-token-stream",
+ "version": "3.1.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/php-token-stream.git",
+ "reference": "995192df77f63a59e47f025390d2d1fdf8f425ff"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/php-token-stream/zipball/995192df77f63a59e47f025390d2d1fdf8f425ff",
+ "reference": "995192df77f63a59e47f025390d2d1fdf8f425ff",
+ "shasum": ""
+ },
+ "require": {
+ "ext-tokenizer": "*",
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Wrapper around PHP's tokenizer extension.",
+ "homepage": "https://github.com/sebastianbergmann/php-token-stream/",
+ "keywords": [
+ "tokenizer"
+ ],
+ "time": "2019-09-17T06:23:10+00:00"
+ },
+ {
+ "name": "phpunit/phpunit",
+ "version": "7.5.17",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/phpunit.git",
+ "reference": "4c92a15296e58191a4cd74cff3b34fc8e374174a"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/4c92a15296e58191a4cd74cff3b34fc8e374174a",
+ "reference": "4c92a15296e58191a4cd74cff3b34fc8e374174a",
+ "shasum": ""
+ },
+ "require": {
+ "doctrine/instantiator": "^1.1",
+ "ext-dom": "*",
+ "ext-json": "*",
+ "ext-libxml": "*",
+ "ext-mbstring": "*",
+ "ext-xml": "*",
+ "myclabs/deep-copy": "^1.7",
+ "phar-io/manifest": "^1.0.2",
+ "phar-io/version": "^2.0",
+ "php": "^7.1",
+ "phpspec/prophecy": "^1.7",
+ "phpunit/php-code-coverage": "^6.0.7",
+ "phpunit/php-file-iterator": "^2.0.1",
+ "phpunit/php-text-template": "^1.2.1",
+ "phpunit/php-timer": "^2.1",
+ "sebastian/comparator": "^3.0",
+ "sebastian/diff": "^3.0",
+ "sebastian/environment": "^4.0",
+ "sebastian/exporter": "^3.1",
+ "sebastian/global-state": "^2.0",
+ "sebastian/object-enumerator": "^3.0.3",
+ "sebastian/resource-operations": "^2.0",
+ "sebastian/version": "^2.0.1"
+ },
+ "conflict": {
+ "phpunit/phpunit-mock-objects": "*"
+ },
+ "require-dev": {
+ "ext-pdo": "*"
+ },
+ "suggest": {
+ "ext-soap": "*",
+ "ext-xdebug": "*",
+ "phpunit/php-invoker": "^2.0"
+ },
+ "bin": [
+ "phpunit"
+ ],
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "7.5-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "The PHP Unit Testing framework.",
+ "homepage": "https://phpunit.de/",
+ "keywords": [
+ "phpunit",
+ "testing",
+ "xunit"
+ ],
+ "time": "2019-10-28T10:37:36+00:00"
+ },
+ {
+ "name": "sebastian/code-unit-reverse-lookup",
+ "version": "1.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/code-unit-reverse-lookup.git",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/code-unit-reverse-lookup/zipball/4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "reference": "4419fcdb5eabb9caa61a27c7a1db532a6b55dd18",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.6 || ^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^5.7 || ^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Looks up which function or method a line of code belongs to",
+ "homepage": "https://github.com/sebastianbergmann/code-unit-reverse-lookup/",
+ "time": "2017-03-04T06:30:41+00:00"
+ },
+ {
+ "name": "sebastian/comparator",
+ "version": "3.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/comparator.git",
+ "reference": "5de4fc177adf9bce8df98d8d141a7559d7ccf6da"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/comparator/zipball/5de4fc177adf9bce8df98d8d141a7559d7ccf6da",
+ "reference": "5de4fc177adf9bce8df98d8d141a7559d7ccf6da",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1",
+ "sebastian/diff": "^3.0",
+ "sebastian/exporter": "^3.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@2bepublished.at"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides the functionality to compare PHP values for equality",
+ "homepage": "https://github.com/sebastianbergmann/comparator",
+ "keywords": [
+ "comparator",
+ "compare",
+ "equality"
+ ],
+ "time": "2018-07-12T15:12:46+00:00"
+ },
+ {
+ "name": "sebastian/diff",
+ "version": "3.0.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/diff.git",
+ "reference": "720fcc7e9b5cf384ea68d9d930d480907a0c1a29"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/720fcc7e9b5cf384ea68d9d930d480907a0c1a29",
+ "reference": "720fcc7e9b5cf384ea68d9d930d480907a0c1a29",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.5 || ^8.0",
+ "symfony/process": "^2 || ^3.3 || ^4"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Kore Nordmann",
+ "email": "mail@kore-nordmann.de"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Diff implementation",
+ "homepage": "https://github.com/sebastianbergmann/diff",
+ "keywords": [
+ "diff",
+ "udiff",
+ "unidiff",
+ "unified diff"
+ ],
+ "time": "2019-02-04T06:01:07+00:00"
+ },
+ {
+ "name": "sebastian/environment",
+ "version": "4.2.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/environment.git",
+ "reference": "f2a2c8e1c97c11ace607a7a667d73d47c19fe404"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/environment/zipball/f2a2c8e1c97c11ace607a7a667d73d47c19fe404",
+ "reference": "f2a2c8e1c97c11ace607a7a667d73d47c19fe404",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^7.5"
+ },
+ "suggest": {
+ "ext-posix": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "4.2-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides functionality to handle HHVM/PHP environments",
+ "homepage": "http://www.github.com/sebastianbergmann/environment",
+ "keywords": [
+ "Xdebug",
+ "environment",
+ "hhvm"
+ ],
+ "time": "2019-05-05T09:05:15+00:00"
+ },
+ {
+ "name": "sebastian/exporter",
+ "version": "3.1.2",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/exporter.git",
+ "reference": "68609e1261d215ea5b21b7987539cbfbe156ec3e"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/exporter/zipball/68609e1261d215ea5b21b7987539cbfbe156ec3e",
+ "reference": "68609e1261d215ea5b21b7987539cbfbe156ec3e",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "ext-mbstring": "*",
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.1.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Volker Dusch",
+ "email": "github@wallbash.com"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ },
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@gmail.com"
+ }
+ ],
+ "description": "Provides the functionality to export PHP variables for visualization",
+ "homepage": "http://www.github.com/sebastianbergmann/exporter",
+ "keywords": [
+ "export",
+ "exporter"
+ ],
+ "time": "2019-09-14T09:02:43+00:00"
+ },
+ {
+ "name": "sebastian/global-state",
+ "version": "2.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/global-state.git",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/global-state/zipball/e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "reference": "e8ba02eed7bbbb9e59e43dedd3dddeff4a56b0c4",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "suggest": {
+ "ext-uopz": "*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Snapshotting of global state",
+ "homepage": "http://www.github.com/sebastianbergmann/global-state",
+ "keywords": [
+ "global state"
+ ],
+ "time": "2017-04-27T15:39:26+00:00"
+ },
+ {
+ "name": "sebastian/object-enumerator",
+ "version": "3.0.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-enumerator.git",
+ "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-enumerator/zipball/7cfd9e65d11ffb5af41198476395774d4c8a84c5",
+ "reference": "7cfd9e65d11ffb5af41198476395774d4c8a84c5",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0",
+ "sebastian/object-reflector": "^1.1.1",
+ "sebastian/recursion-context": "^3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Traverses array structures and object graphs to enumerate all referenced objects",
+ "homepage": "https://github.com/sebastianbergmann/object-enumerator/",
+ "time": "2017-08-03T12:35:26+00:00"
+ },
+ {
+ "name": "sebastian/object-reflector",
+ "version": "1.1.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/object-reflector.git",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/object-reflector/zipball/773f97c67f28de00d397be301821b06708fca0be",
+ "reference": "773f97c67f28de00d397be301821b06708fca0be",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.1-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Allows reflection of object attributes, including inherited and non-public ones",
+ "homepage": "https://github.com/sebastianbergmann/object-reflector/",
+ "time": "2017-03-29T09:07:27+00:00"
+ },
+ {
+ "name": "sebastian/recursion-context",
+ "version": "3.0.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/recursion-context.git",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/recursion-context/zipball/5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "reference": "5b0cd723502bac3b006cbf3dbf7a1e3fcefe4fa8",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^6.0"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "3.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Jeff Welch",
+ "email": "whatthejeff@gmail.com"
+ },
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ },
+ {
+ "name": "Adam Harvey",
+ "email": "aharvey@php.net"
+ }
+ ],
+ "description": "Provides functionality to recursively process PHP variables",
+ "homepage": "http://www.github.com/sebastianbergmann/recursion-context",
+ "time": "2017-03-03T06:23:57+00:00"
+ },
+ {
+ "name": "sebastian/resource-operations",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/resource-operations.git",
+ "reference": "4d7a795d35b889bf80a0cc04e08d77cedfa917a9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/resource-operations/zipball/4d7a795d35b889bf80a0cc04e08d77cedfa917a9",
+ "reference": "4d7a795d35b889bf80a0cc04e08d77cedfa917a9",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^7.1"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de"
+ }
+ ],
+ "description": "Provides a list of PHP built-in functions that operate on resources",
+ "homepage": "https://www.github.com/sebastianbergmann/resource-operations",
+ "time": "2018-10-04T04:07:39+00:00"
+ },
+ {
+ "name": "sebastian/version",
+ "version": "2.0.1",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/sebastianbergmann/version.git",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/sebastianbergmann/version/zipball/99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "reference": "99732be0ddb3361e16ad77b68ba41efc8e979019",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.6"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "2.0.x-dev"
+ }
+ },
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Sebastian Bergmann",
+ "email": "sebastian@phpunit.de",
+ "role": "lead"
+ }
+ ],
+ "description": "Library that helps with managing the version number of Git-hosted PHP projects",
+ "homepage": "https://github.com/sebastianbergmann/version",
+ "time": "2016-10-03T07:35:21+00:00"
+ },
+ {
+ "name": "symfony/polyfill-ctype",
+ "version": "v1.12.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/symfony/polyfill-ctype.git",
+ "reference": "550ebaac289296ce228a706d0867afc34687e3f4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/550ebaac289296ce228a706d0867afc34687e3f4",
+ "reference": "550ebaac289296ce228a706d0867afc34687e3f4",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.3"
+ },
+ "suggest": {
+ "ext-ctype": "For best performance"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.12-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Symfony\\Polyfill\\Ctype\\": ""
+ },
+ "files": [
+ "bootstrap.php"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Gert de Pagter",
+ "email": "BackEndTea@gmail.com"
+ },
+ {
+ "name": "Symfony Community",
+ "homepage": "https://symfony.com/contributors"
+ }
+ ],
+ "description": "Symfony polyfill for ctype functions",
+ "homepage": "https://symfony.com",
+ "keywords": [
+ "compatibility",
+ "ctype",
+ "polyfill",
+ "portable"
+ ],
+ "time": "2019-08-06T08:03:45+00:00"
+ },
+ {
+ "name": "theseer/tokenizer",
+ "version": "1.1.3",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/theseer/tokenizer.git",
+ "reference": "11336f6f84e16a720dae9d8e6ed5019efa85a0f9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/theseer/tokenizer/zipball/11336f6f84e16a720dae9d8e6ed5019efa85a0f9",
+ "reference": "11336f6f84e16a720dae9d8e6ed5019efa85a0f9",
+ "shasum": ""
+ },
+ "require": {
+ "ext-dom": "*",
+ "ext-tokenizer": "*",
+ "ext-xmlwriter": "*",
+ "php": "^7.0"
+ },
+ "type": "library",
+ "autoload": {
+ "classmap": [
+ "src/"
+ ]
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "BSD-3-Clause"
+ ],
+ "authors": [
+ {
+ "name": "Arne Blankerts",
+ "email": "arne@blankerts.de",
+ "role": "Developer"
+ }
+ ],
+ "description": "A small library for converting tokenized PHP source code into XML and potentially other formats",
+ "time": "2019-06-13T22:48:21+00:00"
+ },
+ {
+ "name": "webmozart/assert",
+ "version": "1.5.0",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/webmozart/assert.git",
+ "reference": "88e6d84706d09a236046d686bbea96f07b3a34f4"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/webmozart/assert/zipball/88e6d84706d09a236046d686bbea96f07b3a34f4",
+ "reference": "88e6d84706d09a236046d686bbea96f07b3a34f4",
+ "shasum": ""
+ },
+ "require": {
+ "php": "^5.3.3 || ^7.0",
+ "symfony/polyfill-ctype": "^1.8"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "^4.8.36 || ^7.5.13"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.3-dev"
+ }
+ },
+ "autoload": {
+ "psr-4": {
+ "Webmozart\\Assert\\": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Bernhard Schussek",
+ "email": "bschussek@gmail.com"
+ }
+ ],
+ "description": "Assertions to validate method input/output with nice error messages.",
+ "keywords": [
+ "assert",
+ "check",
+ "validate"
+ ],
+ "time": "2019-08-24T08:43:50+00:00"
+ }
+ ],
"aliases": [],
"minimum-stability": "stable",
"stability-flags": [],
@@ -15,7 +1485,6 @@
"platform": {
"php": ">=5.6",
"ext-mbstring": "*",
- "ext-sqlite3": "*",
"ext-curl": "*",
"ext-openssl": "*",
"ext-libxml": "*",
diff --git a/config.default.ini.php b/config.default.ini.php
index b7d4fba..7d0bdaa 100644
--- a/config.default.ini.php
+++ b/config.default.ini.php
@@ -61,6 +61,18 @@ username = ""
; Use a strong password to prevent others from guessing your login!
password = ""
+[error]
+
+; Defines how error messages are returned by RSS-Bridge
+;
+; "feed" = As part of the feed (default)
+; "http" = As HTTP error message
+; "none" = No errors are reported
+output = "feed"
+
+; Defines how often an error must occur before it is reported to the user
+report_limit = 1
+
; --- Cache specific configuration ---------------------------------------------
[SQLiteCache]
diff --git a/formats/AtomFormat.php b/formats/AtomFormat.php
index 1159a61..a1ecfcf 100644
--- a/formats/AtomFormat.php
+++ b/formats/AtomFormat.php
@@ -7,6 +7,8 @@
* https://validator.w3.org/feed/
*/
class AtomFormat extends FormatAbstract{
+ const MIME_TYPE = 'application/atom+xml';
+
const LIMIT_TITLE = 140;
public function stringify(){
@@ -147,7 +149,7 @@ EOD;
public function display(){
$this
- ->setContentType('application/atom+xml; charset=' . $this->getCharset())
+ ->setContentType(self::MIME_TYPE . '; charset=' . $this->getCharset())
->callContentType();
return parent::display();
diff --git a/formats/HtmlFormat.php b/formats/HtmlFormat.php
index ebb6b78..49d9ca6 100644
--- a/formats/HtmlFormat.php
+++ b/formats/HtmlFormat.php
@@ -1,5 +1,7 @@
<?php
class HtmlFormat extends FormatAbstract {
+ const MIME_TYPE = 'text/html';
+
public function stringify(){
$extraInfos = $this->getExtraInfos();
$title = htmlspecialchars($extraInfos['name']);
@@ -10,6 +12,7 @@ class HtmlFormat extends FormatAbstract {
$formatFac->setWorkingDir(PATH_LIB_FORMATS);
$buttons = '';
+ $links = '';
foreach($formatFac->getFormatNames() as $format) {
if(strcasecmp($format, 'HTML') === 0) {
@@ -18,6 +21,9 @@ class HtmlFormat extends FormatAbstract {
$query = str_replace('format=Html', 'format=' . $format, htmlentities($_SERVER['QUERY_STRING']));
$buttons .= $this->buildButton($format, $query) . PHP_EOL;
+
+ $mime = $formatFac->create($format)->getMimeType();
+ $links .= $this->buildLink($format, $query, $mime) . PHP_EOL;
}
$entries = '';
@@ -99,6 +105,7 @@ EOD;
<title>{$title}</title>
<link href="static/HtmlFormat.css" rel="stylesheet">
<link rel="icon" type="image/png" href="static/favicon.png">
+ {$links}
<meta name="robots" content="noindex, follow">
</head>
<body>
@@ -120,7 +127,7 @@ EOD;
public function display() {
$this
- ->setContentType('text/html; charset=' . $this->getCharset())
+ ->setContentType(self::MIME_TYPE . '; charset=' . $this->getCharset())
->callContentType();
return parent::display();
@@ -131,4 +138,11 @@ EOD;
<a href="./?{$query}"><button class="rss-feed">{$format}</button></a>
EOD;
}
+
+ private function buildLink($format, $query, $mime) {
+ return <<<EOD
+<link href="./?{$query}" title="{$format}" rel="alternate" type="{$mime}">
+
+EOD;
+ }
}
diff --git a/formats/JsonFormat.php b/formats/JsonFormat.php
index 5d09162..2c5cd07 100644
--- a/formats/JsonFormat.php
+++ b/formats/JsonFormat.php
@@ -8,6 +8,8 @@
* https://github.com/vigetlabs/json-feed-validator
*/
class JsonFormat extends FormatAbstract {
+ const MIME_TYPE = 'application/json';
+
const VENDOR_EXCLUDES = array(
'author',
'title',
@@ -119,7 +121,7 @@ class JsonFormat extends FormatAbstract {
public function display(){
$this
- ->setContentType('application/json; charset=' . $this->getCharset())
+ ->setContentType(self::MIME_TYPE . '; charset=' . $this->getCharset())
->callContentType();
return parent::display();
diff --git a/formats/MrssFormat.php b/formats/MrssFormat.php
index 836a361..8bf569a 100644
--- a/formats/MrssFormat.php
+++ b/formats/MrssFormat.php
@@ -25,6 +25,8 @@
* RSS 2.0 feed that works with feed readers that don't support the extension.
*/
class MrssFormat extends FormatAbstract {
+ const MIME_TYPE = 'application/rss+xml';
+
const ALLOWED_IMAGE_EXT = array(
'.gif', '.jpg', '.png'
);
@@ -150,7 +152,7 @@ EOD;
public function display(){
$this
- ->setContentType('application/rss+xml; charset=' . $this->getCharset())
+ ->setContentType(self::MIME_TYPE . '; charset=' . $this->getCharset())
->callContentType();
return parent::display();
diff --git a/formats/PlaintextFormat.php b/formats/PlaintextFormat.php
index 591a4b3..5a0522c 100644
--- a/formats/PlaintextFormat.php
+++ b/formats/PlaintextFormat.php
@@ -4,6 +4,8 @@
* Returns $this->items as raw php data.
*/
class PlaintextFormat extends FormatAbstract {
+ const MIME_TYPE = 'text/plain';
+
public function stringify(){
$items = $this->getItems();
$data = array();
@@ -22,7 +24,7 @@ class PlaintextFormat extends FormatAbstract {
public function display(){
$this
- ->setContentType('text/plain; charset=' . $this->getCharset())
+ ->setContentType(self::MIME_TYPE . '; charset=' . $this->getCharset())
->callContentType();
return parent::display();
diff --git a/lib/BridgeAbstract.php b/lib/BridgeAbstract.php
index b4eb9ff..c8ad79c 100644
--- a/lib/BridgeAbstract.php
+++ b/lib/BridgeAbstract.php
@@ -165,8 +165,8 @@ abstract class BridgeAbstract implements BridgeInterface {
foreach(static::PARAMETERS['global'] as $name => $properties) {
if(isset($inputs[$name])) {
$value = $inputs[$name];
- } elseif(isset($properties['value'])) {
- $value = $properties['value'];
+ } elseif(isset($properties['defaultValue'])) {
+ $value = $properties['defaultValue'];
} else {
continue;
}
diff --git a/lib/BridgeCard.php b/lib/BridgeCard.php
index c6f3822..4353f64 100644
--- a/lib/BridgeCard.php
+++ b/lib/BridgeCard.php
@@ -122,6 +122,11 @@ This bridge is not fetching its content through a secure connection</div>';
} elseif($inputEntry['type'] === 'checkbox') {
$form .= self::getCheckboxInput($inputEntry, $idArg, $id);
}
+
+ if(isset($inputEntry['title']))
+ $form .= '<i class="info" title="' . filter_var($inputEntry['title'], FILTER_SANITIZE_STRING) . '">i</i>';
+ else
+ $form .= '<i></i>';
}
$form .= '</div>';
@@ -152,9 +157,6 @@ This bridge is not fetching its content through a secure connection</div>';
if(isset($entry['pattern']))
$retVal .= ' pattern="' . $entry['pattern'] . '"';
- if(isset($entry['title']))
- $retVal .= ' title="' . filter_var($entry['title'], FILTER_SANITIZE_STRING) . '"';
-
return $retVal;
}
diff --git a/lib/Configuration.php b/lib/Configuration.php
index fc575d6..6d52423 100644
--- a/lib/Configuration.php
+++ b/lib/Configuration.php
@@ -28,7 +28,7 @@ final class Configuration {
*
* @todo Replace this property by a constant.
*/
- public static $VERSION = '2019-09-12';
+ public static $VERSION = '2019-12-01';
/**
* Holds the configuration data.
@@ -201,6 +201,13 @@ final class Configuration {
&& !filter_var(self::getConfig('admin', 'email'), FILTER_VALIDATE_EMAIL))
self::reportConfigurationError('admin', 'email', 'Is not a valid email address');
+ if(!is_string(self::getConfig('error', 'output')))
+ self::reportConfigurationError('error', 'output', 'Is not a valid String');
+
+ if(!is_numeric(self::getConfig('error', 'report_limit'))
+ || self::getConfig('error', 'report_limit') < 1)
+ self::reportConfigurationError('admin', 'report_limit', 'Value is invalid');
+
}
/**
diff --git a/lib/FormatAbstract.php b/lib/FormatAbstract.php
index 5395d56..5c4b87f 100644
--- a/lib/FormatAbstract.php
+++ b/lib/FormatAbstract.php
@@ -21,6 +21,9 @@ abstract class FormatAbstract implements FormatInterface {
/** The default charset (UTF-8) */
const DEFAULT_CHARSET = 'UTF-8';
+ /** MIME type of format output */
+ const MIME_TYPE = 'text/plain';
+
/** @var string|null $contentType The content type */
protected $contentType = null;
@@ -39,6 +42,11 @@ abstract class FormatAbstract implements FormatInterface {
/** @var array $extraInfos The extra infos */
protected $extraInfos;
+ /** {@inheritdoc} */
+ public function getMimeType(){
+ return static::MIME_TYPE;
+ }
+
/**
* {@inheritdoc}
*
diff --git a/lib/FormatInterface.php b/lib/FormatInterface.php
index 68b0bd5..82049d4 100644
--- a/lib/FormatInterface.php
+++ b/lib/FormatInterface.php
@@ -67,6 +67,13 @@ interface FormatInterface {
public function getExtraInfos();
/**
+ * Return MIME type
+ *
+ * @return string The MIME type
+ */
+ public function getMimeType();
+
+ /**
* Set charset
*
* @param string $charset The charset
diff --git a/lib/ParameterValidator.php b/lib/ParameterValidator.php
index f740888..149e8a4 100644
--- a/lib/ParameterValidator.php
+++ b/lib/ParameterValidator.php
@@ -191,6 +191,13 @@ class ParameterValidator {
foreach($parameters as $context => $set) {
$queriedContexts[$context] = null;
+ // Ensure all user data exist in the current context
+ $notInContext = array_diff_key($data, $set);
+ if(array_key_exists('global', $parameters))
+ $notInContext = array_diff_key($notInContext, $parameters['global']);
+ if(sizeof($notInContext) > 0)
+ continue;
+
// Check if all parameters of the context are satisfied
foreach($set as $id => $properties) {
if(isset($data[$id]) && !empty($data[$id])) {
diff --git a/lib/contents.php b/lib/contents.php
index 8649c0b..b1e3128 100644
--- a/lib/contents.php
+++ b/lib/contents.php
@@ -37,11 +37,13 @@
* @param array $opts (optional) A list of cURL options as associative array in
* the format `$opts[$option] = $value;`, where `$option` is any `CURLOPT_XXX`
* option and `$value` the corresponding value.
+ * @param bool $returnHeader Returns an array of two elements 'header' and
+ * 'content' if enabled.
*
* For more information see http://php.net/manual/en/function.curl-setopt.php
* @return string The contents.
*/
-function getContents($url, $header = array(), $opts = array()){
+function getContents($url, $header = array(), $opts = array(), $returnHeader = false){
Debug::log('Reading contents from "' . $url . '"');
// Initialize cache
@@ -51,9 +53,14 @@ function getContents($url, $header = array(), $opts = array()){
$cache->setScope('server');
$cache->purgeCache(86400); // 24 hours (forced)
- $params = [$url];
+ $params = array($url);
$cache->setKey($params);
+ $retVal = array(
+ 'header' => '',
+ 'content' => '',
+ );
+
// Use file_get_contents if in CLI mode with no root certificates defined
if(php_sapi_name() === 'cli' && empty(ini_get('curl.cainfo'))) {
@@ -141,6 +148,7 @@ function getContents($url, $header = array(), $opts = array()){
$headerSize = curl_getinfo($ch, CURLINFO_HEADER_SIZE);
$header = substr($data, 0, $headerSize);
+ $retVal['header'] = $header;
Debug::log('Response header: ' . $header);
@@ -164,15 +172,18 @@ function getContents($url, $header = array(), $opts = array()){
if(in_array('no-cache', $directives)
|| in_array('no-store', $directives)) { // Skip caching
Debug::log('Skip server side caching');
- return $data;
+ $retVal['content'] = $data;
+ break;
}
}
Debug::log('Store response to cache');
$cache->saveData($data);
- return $data;
+ $retVal['content'] = $data;
+ break;
case 304: // Not modified, use cached data
Debug::log('Contents not modified on host, returning cached data');
- return $cache->loadData();
+ $retVal['content'] = $cache->loadData();
+ break;
default:
if(array_key_exists('Server', $finalHeader) && strpos($finalHeader['Server'], 'cloudflare') !== false) {
returnServerError(<<< EOD
@@ -193,6 +204,8 @@ PHP error: $lastError
EOD
, $errorCode);
}
+
+ return ($returnHeader === true) ? $retVal : $retVal['content'];
}
/**
@@ -291,7 +304,7 @@ function getSimpleHTMLDOMCached($url,
$cache->setScope('pages');
$cache->purgeCache(86400); // 24 hours (forced)
- $params = [$url];
+ $params = array($url);
$cache->setKey($params);
// Determine if cached file is within duration
diff --git a/lib/error.php b/lib/error.php
index 9a0756f..4b7110f 100644
--- a/lib/error.php
+++ b/lib/error.php
@@ -41,3 +41,37 @@ function returnClientError($message){
function returnServerError($message){
returnError($message, 500);
}
+
+/**
+ * Stores bridge-specific errors in a cache file.
+ *
+ * @param string $bridgeName The name of the bridge that failed.
+ * @param int $code The error code
+ *
+ * @return int The total number the same error has appeared
+ */
+function logBridgeError($bridgeName, $code) {
+ $cacheFac = new CacheFactory();
+ $cacheFac->setWorkingDir(PATH_LIB_CACHES);
+
+ $cache = $cacheFac->create(Configuration::getConfig('cache', 'type'));
+ $cache->setScope('error_reporting');
+ $cache->setkey($bridgeName . '_' . $code);
+ $cache->purgeCache(86400); // 24 hours
+
+ if($report = $cache->loadData()) {
+ $report = json_decode($report, true);
+ $report['time'] = time();
+ $report['count']++;
+ } else {
+ $report = array(
+ 'error' => $code,
+ 'time' => time(),
+ 'count' => 1,
+ );
+ }
+
+ $cache->saveData(json_encode($report));
+
+ return $report['count'];
+}
diff --git a/static/connectivity.css b/static/connectivity.css
new file mode 100644
index 0000000..5f891d2
--- /dev/null
+++ b/static/connectivity.css
@@ -0,0 +1,8 @@
+input:focus::-webkit-input-placeholder { opacity: 0; }
+input:focus::-moz-placeholder { opacity: 0; }
+input:focus::placeholder { opacity: 0; }
+input:focus:-moz-placeholder { opacity: 0; }
+input:focus:-ms-input-placeholder { opacity: 0; }
+
+.progress { height: 2px; }
+.progressbar { width: 0%; } \ No newline at end of file
diff --git a/static/connectivity.js b/static/connectivity.js
new file mode 100644
index 0000000..89f01f0
--- /dev/null
+++ b/static/connectivity.js
@@ -0,0 +1,256 @@
+var remote = location.href.substring(0, location.href.lastIndexOf("/"));
+var bridges = [];
+var abort = false;
+
+window.onload = function() {
+
+ fetch(remote + '/index.php?action=list').then(function(response) {
+ return response.text()
+ }).then(function(data){
+ processBridgeList(data);
+ }).catch(console.log.bind(console)
+ );
+
+}
+
+function processBridgeList(data) {
+
+ var list = JSON.parse(data);
+
+ buildTable(list);
+ buildBridgeQueue(list);
+ checkNextBridgeAsync();
+
+}
+
+function buildTable(bridgeList) {
+
+ var table = document.createElement('table');
+ table.classList.add('table');
+
+ var thead = document.createElement('thead');
+ thead.innerHTML = `
+ <tr>
+ <th scope="col">Bridge</th>
+ <th scope="col">Result</th>
+ </tr>`;
+
+ var tbody = document.createElement('tbody');
+
+ for (var bridge in bridgeList.bridges) {
+
+ var tr = document.createElement('tr');
+ tr.classList.add('bg-secondary');
+ tr.id = bridge;
+
+ var td_bridge = document.createElement('td');
+ td_bridge.innerText = bridgeList.bridges[bridge].name;
+
+ // Link to the actual bridge on index.php
+ var a = document.createElement('a');
+ a.href = remote + "/index.php?show_inactive=1#bridge-" + bridge;
+ a.target = '_blank';
+ a.innerText = '[Show]';
+ a.style.marginLeft = '5px';
+ a.style.color = 'black';
+
+ td_bridge.appendChild(a);
+ tr.appendChild(td_bridge);
+
+ var td_result = document.createElement('td');
+
+ if (bridgeList.bridges[bridge].status === 'active') {
+ td_result.innerHTML = '<i title="Scheduled" class="fas fa-hourglass-start"></i>';
+ } else {
+ td_result.innerHTML = '<i title="Inactive" class="fas fa-times-circle"></i>';
+ }
+
+ tr.appendChild(td_result);
+ tbody.appendChild(tr);
+
+ }
+
+ table.appendChild(thead);
+ table.appendChild(tbody);
+
+ var content = document.getElementById('main-content');
+ content.appendChild(table);
+
+}
+
+function buildBridgeQueue(bridgeList) {
+ for (var bridge in bridgeList.bridges) {
+ if (bridgeList.bridges[bridge].status !== 'active')
+ continue;
+ bridges.push(bridge);
+ }
+}
+
+
+function checkNextBridgeAsync() {
+ return new Promise((resolve) => {
+ var msg = document.getElementById('status-message');
+ var icon = document.getElementById('status-icon');
+
+ if (bridges.length === 0) {
+ msg.classList.remove('alert-primary');
+ msg.classList.add('alert-success');
+ msg.getElementsByTagName('span')[0].textContent = 'Done';
+
+ icon.classList.remove('fa-sync');
+ icon.classList.add('fa-check');
+ } else {
+ var bridge = bridges.shift();
+
+ msg.getElementsByTagName('span')[0].textContent = 'Processing ' + bridge + '...';
+
+ fetch(remote + '/index.php?action=Connectivity&bridge=' + bridge)
+ .then(function(response) { return response.text() })
+ .then(JSON.parse)
+ .then(processBridgeResultAsync)
+ .then(markBridgeSuccessful, markBridgeFailed)
+ .then(checkAbortAsync)
+ .then(checkNextBridgeAsync, abortChecks)
+ .catch(console.log.bind(console));
+
+ search(); // Dynamically update search results
+ updateProgressBar();
+
+ }
+
+ resolve();
+ });
+}
+
+function abortChecks() {
+ return new Promise((resolve) => {
+ var msg = document.getElementById('status-message');
+
+ msg.classList.remove('alert-primary');
+ msg.classList.add('alert-warning');
+ msg.getElementsByTagName('span')[0].textContent = 'Aborted';
+
+ var icon = document.getElementById('status-icon');
+ icon.classList.remove('fa-sync');
+ icon.classList.add('fa-ban');
+
+ bridges.forEach((bridge) => {
+ markBridgeAborted(bridge);
+ })
+
+ resolve();
+ });
+}
+
+function processBridgeResultAsync(result) {
+ return new Promise((resolve, reject) => {
+ if (result.successful) {
+ resolve(result);
+ } else {
+ reject(result);
+ }
+ });
+}
+
+function markBridgeSuccessful(result) {
+ return new Promise((resolve) => {
+ var tr = document.getElementById(result.bridge);
+ tr.classList.remove('bg-secondary');
+ if (result.http_code == 200) {
+ tr.classList.add('bg-success');
+ tr.children[1].innerHTML = '<i title="Successful" class="fas fa-check"></i>';
+ } else {
+ tr.classList.add('bg-primary');
+ tr.children[1].innerHTML = '<i title="Redirected" class="fas fa-directions"></i>';
+ }
+
+ resolve();
+ });
+}
+
+function markBridgeFailed(result) {
+ return new Promise((resolve) => {
+ var tr = document.getElementById(result.bridge);
+ tr.classList.remove('bg-secondary');
+ tr.classList.add('bg-danger');
+ tr.children[1].innerHTML = '<i title="Failed" class="fas fa-exclamation-triangle"></i>';
+
+ resolve();
+ });
+}
+
+function markBridgeAborted(bridge) {
+ return new Promise((resolve) => {
+ var tr = document.getElementById(bridge);
+ tr.classList.remove('bg-secondary');
+ tr.classList.add('bg-warning');
+ tr.children[1].innerHTML = '<i title="Aborted" class="fas fa-ban"></i>';
+
+ resolve();
+ });
+}
+
+function checkAbortAsync() {
+ return new Promise((resolve, reject) => {
+ if (abort) {
+ reject();
+ return;
+ }
+
+ resolve();
+ });
+}
+
+function updateProgressBar() {
+
+ // This will break if the table changes
+ var total = document.getElementsByTagName('tr').length - 1;
+ var current = bridges.length;
+ var progress = (total - current) * 100 / total;
+
+ var progressBar = document.getElementsByClassName('progress-bar')[0];
+
+ if(progressBar){
+ progressBar.setAttribute('aria-valuenow', progress.toFixed(0));
+ progressBar.style.width = progress.toFixed(0) + '%';
+ }
+
+}
+
+function stopConnectivityChecks() {
+ abort = true;
+}
+
+function search() {
+
+ var input = document.getElementById('search');
+ var filter = input.value.toUpperCase();
+ var table = document.getElementsByTagName('table')[0];
+ var tr = table.getElementsByTagName('tr');
+
+ for (var i = 0; i < tr.length; i++) {
+
+ var td1 = tr[i].getElementsByTagName('td')[0];
+ var td2 = tr[i].getElementsByTagName('td')[1];
+
+ if (td1) {
+
+ var txtValue = td1.textContent || td1.innerText;
+
+ var title = '';
+ if(td2.getElementsByTagName('i')[0]) {
+ title = td2.getElementsByTagName('i')[0].title;
+ }
+
+ if (txtValue.toUpperCase().indexOf(filter) > -1
+ || title.toUpperCase().indexOf(filter) > -1) {
+ tr[i].style.display = '';
+ } else {
+ tr[i].style.display = 'none';
+ }
+
+ }
+
+ }
+
+} \ No newline at end of file
diff --git a/static/style.css b/static/style.css
index 974aa78..5df2c51 100644
--- a/static/style.css
+++ b/static/style.css
@@ -184,12 +184,33 @@ form {
content: ' :';
}
+.info {
+ cursor: help;
+ opacity: 0.5;
+ width: 24px;
+ height: 24px;
+ font-size: 16px;
+ font-weight: bold;
+ font-style: italic;
+ line-height: 22px;
+ text-align: center;
+ color: #fff;
+ background-image: radial-gradient(#49afff, #1182DB);
+ -webkit-border-radius: 16px;
+ -moz-border-radius: 16px;
+ border-radius: 16px;
+}
+
+.info:hover {
+ opacity: 1;
+}
+
@supports (display: grid) {
.parameters {
display: grid;
padding: 12px 0;
- grid-template-columns: 40% max-content;
+ grid-template-columns: 40% max-content 24px;
grid-column-gap: 10px;
grid-row-gap: 5px;
}
@@ -339,6 +360,10 @@ h5 {
margin: 3px auto 0;
}
+ .info {
+ display: none;
+ }
+
@supports (display: grid) {
.parameters {