diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..5b67882 --- /dev/null +++ b/.gitattributes @@ -0,0 +1,14 @@ +* text=auto + +/tests export-ignore +/.gitattributes export-ignore +/.gitignore export-ignore +/.scrutinizer.yml export-ignore +/.sensiolabs.yml export-ignore +/.styleci.yml export-ignore +/.travis.yml export-ignore +/CHANGELOG.md export-ignore +/CONTRIBUTING.md export-ignore +/phpunit.xml.dist export-ignore +/README.md export-ignore +/ruleset.xml export-ignore diff --git a/.gitignore b/.gitignore index f0bb242..81b9258 100644 --- a/.gitignore +++ b/.gitignore @@ -1,23 +1,3 @@ -.DS_Store -._* -.Spotlight-V100 -.Trashes -Thumbs.db -Desktop.ini -*.sassc -*.scssc -compass_app_log.txt -/.sass-cache/ -/.idea/ -/.vagrant/ -/project.xml -/phpunit.xml -/phpunit.phar -/composer.phar -/composer.lock -/vendor/ -/bower_components/ -/node_modules/ -/npm-debug.log -/stylesheets/ -build.txt +composer.lock +phpunit.xml +vendor diff --git a/.scrutinizer.yml b/.scrutinizer.yml new file mode 100644 index 0000000..42b6c74 --- /dev/null +++ b/.scrutinizer.yml @@ -0,0 +1,16 @@ +tools: + php_cs_fixer: + config: + level: psr2 + php_code_sniffer: + config: + standard: "PSR2" + +build: + tests: + override: + - + command: 'phpunit --coverage-clover=phpunit-coverage.xml' + coverage: + file: 'phpunit-coverage.xml' + format: 'php-clover' diff --git a/.sensiolabs.yml b/.sensiolabs.yml new file mode 100644 index 0000000..f0e056f --- /dev/null +++ b/.sensiolabs.yml @@ -0,0 +1,3 @@ +rules: + php.bad_mutator_method_name_for_boolean_property: + enabled: false diff --git a/.styleci.yml b/.styleci.yml new file mode 100644 index 0000000..247a09c --- /dev/null +++ b/.styleci.yml @@ -0,0 +1 @@ +preset: psr2 diff --git a/.travis.yml b/.travis.yml index 27a9979..aa5f09d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -4,19 +4,14 @@ env: - APP_ENV=travis php: - - 5.4 - - 5.5 - - 5.6 + - 7.2 + - 7.3 + - 7.4 + - nightly #php 8 - hhvm before_script: - ## Composer - - composer self-update - - composer install --prefer-source --no-interaction --dev + - composer install --no-interaction script: - phpunit - -matrix: - allow_failures: - - php: hhvm diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 0000000..bb0199d --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,72 @@ +# CHANGELOG + +## 6.1.2 (released 2016-12-28) + +- Added wkhtmltopdf detection + +## 6.1.1 (released 2016-12-13) + +- Added Samsung Browser detection + +## 6.1.0 (released 2016-10-28) + +- Fixed issue with blackberry version detection + +## 6.0.5 (released 2016-07-28) + +- Windows Phone now marks OS as mobile + +## 6.0.4 (released 2016-07-27) + +- Fixed Windows Phone detection +- Added Lumia device detection + +## 6.0.3 (released 2016-07-25) + +- Fixed BB10 detection + +## 6.0.2 (released 2016-06-30) + +- Added Comodo Dragon detection + +## 6.0.1 (released 2016-04-09) + +- Added Facebook WebView detection + +## 6.0.0 (released 2016-01-18) + +- Standardized versions type to string + +## 5.1.2 (released 2016-01-08) + +- Added Chrome OS detection + +## 5.1.1 (released 2015-12-08) + +- Fixed several issues when bad user agents were passed + +## 5.1.0 (released 2015-11-16) + +- Reactored the device class + +## 5.0.1 (released 2015-09-16) + +- Added Vivaldi detection + +## 5.0.0 (released 2015-09-07) + +- Changed namespace from Browser to Sinergi\BrowserDetector + +## 4.0.1 (released 2015-09-07) + +- Added Windows 10 detection +- Added more OS detection unit tests + +## 4.0.0 (released 2015-08-22) + +- Refactoring +- Detect Yandex browser +- Detect latest Opera Mini browser +- Detect iPhone Device +- More unit tests +- Microsoft Edge detection diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..0ca2ed1 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,32 @@ +# CONTRIBUTING + +Contributions are welcome, and are accepted via pull requests. Please review these guidelines before submitting any pull requests. + +## Guidelines + +* Please follow the [PSR-2 Coding Standard](https://github.com/php-fig/fig-standards/blob/master/accepted/PSR-2-coding-style-guide.md) and [PHP-FIG Naming Conventions](https://github.com/php-fig/fig-standards/blob/master/bylaws/002-psr-naming-conventions.md). +* Ensure that the current tests pass, and if you've added something new, add the tests where relevant. +* Remember that we follow [SemVer](http://semver.org). If you are changing the behaviour, or the public api, you may need to update the docs. +* Send a coherent commit history, making sure each individual commit in your pull request is meaningful. If you had to make multiple intermediate commits while developing, please [squash](http://git-scm.com/book/en/Git-Tools-Rewriting-History) them before submitting. +* You may also need to [rebase](http://git-scm.com/book/en/Git-Branching-Rebasing) to avoid merge conflicts. + + +## Running Tests + +You will need an install of [Composer](https://getcomposer.org) before continuing. + +First, install the dependencies: + +```bash +$ composer install +``` + +Then run phpunit: + +```bash +$ vendor/bin/phpunit +``` + +If the test suite passes on your local machine you should be good to go. + +When you make a pull request, the tests will automatically be run again by [Travis CI](https://travis-ci.org/) on multiple php versions and hhvm. diff --git a/LICENSE b/LICENSE index 3d6acc2..dfe9a79 100644 --- a/LICENSE +++ b/LICENSE @@ -1,7 +1,20 @@ -Copyright (c) 2013 Chris Schuld +The MIT License (MIT) -Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: +Copyright (c) 2013-2017 Chris Schuld -The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. +Permission is hereby granted, free of charge, to any person obtaining a copy of +this software and associated documentation files (the "Software"), to deal in +the Software without restriction, including without limitation the rights to +use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of +the Software, and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. \ No newline at end of file +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS +FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR +COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/README.md b/README.md old mode 100755 new mode 100644 index 7c71c3f..cee8a05 --- a/README.md +++ b/README.md @@ -1,10 +1,15 @@ -PHP Browser -=========== - -[![Build Status](https://img.shields.io/travis/gabrielbull/php-browser/master.svg?style=flat)](https://travis-ci.org/gabrielbull/php-browser) -[![Latest Stable Version](http://img.shields.io/packagist/v/gabrielbull/browser.svg?style=flat)](https://packagist.org/packages/gabrielbull/browser) -[![Total Downloads](https://img.shields.io/packagist/dt/gabrielbull/browser.svg?style=flat)](https://packagist.org/packages/gabrielbull/browser) -[![License](https://img.shields.io/packagist/l/gabrielbull/browser.svg?style=flat)](https://packagist.org/packages/gabrielbull/browser) +Browser Detector +================ + +[![Build Status](https://travis-ci.org/sinergi/php-browser-detector.svg?branch=master)](https://travis-ci.org/sinergi/php-browser-detector) +[![StyleCI](https://styleci.io/repos/3752453/shield?style=flat)](https://styleci.io/repos/3752453) +[![Scrutinizer Code Quality](https://scrutinizer-ci.com/g/sinergi/php-browser-detector/badges/quality-score.png?b=master)](https://scrutinizer-ci.com/g/sinergi/php-browser-detector/?branch=master) +[![Code Coverage](https://scrutinizer-ci.com/g/sinergi/php-browser-detector/badges/coverage.png?b=master)](https://scrutinizer-ci.com/g/sinergi/php-browser-detector/?branch=master) +[![Latest Stable Version](http://img.shields.io/packagist/v/sinergi/browser-detector.svg?style=flat)](https://packagist.org/packages/sinergi/browser-detector) +[![Total Downloads](https://img.shields.io/packagist/dt/sinergi/browser-detector.svg?style=flat)](https://packagist.org/packages/sinergi/browser-detector) +[![License](https://img.shields.io/packagist/l/sinergi/browser-detector.svg?style=flat)](https://packagist.org/packages/sinergi/browser-detector) +[![SensioLabsInsight](https://insight.sensiolabs.com/projects/1865a02e-284c-428a-a2b4-091c997e5935/mini.png)](https://insight.sensiolabs.com/projects/1865a02e-284c-428a-a2b4-091c997e5935) +[![Join the chat at https://gitter.im/sinergi/php-browser-detector](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/sinergi/php-browser-detector?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge) Detecting the user's browser, operating system, device and language from PHP. Because browser detection is not always reliable and evolves at all time, use with care and feel free to contribute. @@ -15,27 +20,25 @@ This library uses PHP 5.3+. ## Install -It is recommended that you install the PHP Browser library [through composer](http://getcomposer.org). To do so, add the following lines to your composer.json file. +It is recommended that you install the PHP Browser library [through composer](http://getcomposer.org). To do so, run the following command: -```JSON -{ - "require": { - "gabrielbull/browser": "dev-master" - } -} +```sh +composer require sinergi/browser-detector ``` ## Browser Detection -The Browser class allow you to detect a user's browser and version. +The Browser class allows you to detect a user's browser and version. ### Browsers Detected + * Vivaldi * Opera * Opera Mini * WebTV * Internet Explorer * Pocket Internet Explorer + * Microsoft Edge * Konqueror * iCab * OmniWeb @@ -63,28 +66,49 @@ The Browser class allow you to detect a user's browser and version. * NetPositive * Phoenix * SeaMonkey + * Yandex Browser + * Comodo Dragon + * Samsung Browser + * wkhtmltopdf ### Usage ```php -use Browser\Browser; +use Sinergi\BrowserDetector\Browser; + +$browser = new Browser(); + +if ($browser->getName() === Browser::IE && $browser->getVersion() < 11) { + echo 'Please upgrade your browser.'; +} +``` + +#### Compatibility Mode + +Detect if Internet Explorer is in Compatibility Mode and send the correct header to have the browser render the page in its standard mode. This must be called before any output is sent to the browser. + +```php +use Sinergi\BrowserDetector\Browser; -$browser = new Browser; -if ($browser->getName() === $browser::IE && $browser->getVersion() < 8) { - echo 'Please upgrade your browser.'; +$browser = new Browser(); + +if ($browser->getName() === Browser::IE && $browser->isCompatibilityMode()) { + $browser->endCompatibilityMode(); } ``` ## OS Detection -The OS class allow you to detect a user's operating system and version. +The OS class allows you to detect a user's operating system and version. ### OS Detected * Windows + * Windows Phone * OS X * iOS * Android + * Chrome OS * Linux * SymbOS * Nokia @@ -100,44 +124,54 @@ The OS class allow you to detect a user's operating system and version. ### Usage ```php -use Browser\Os; +use Sinergi\BrowserDetector\Os; + +$os = new Os(); -$os = new Os; -if ($os->getName() == $os::IOS) { - echo 'You are using an iOS device.'; +if ($os->getName() === Os::IOS) { + echo 'You are using an iOS device.'; } ``` ## Device Detection -The Device class allow you to detect a user's device. +The Device class allows you to detect a user's device. ### Device Detected * iPad + * iPhone + * Windows Phone + * Lumia ### Usage ```php -use Browser\Device; +use Sinergi\BrowserDetector\Device; -$device = new Device; -if ($device->getName() == $device::IPAD) { - echo 'You are using an iPad.'; +$device = new Device(); + +if ($device->getName() === Device::IPAD) { + echo 'You are using an iPad.'; } ``` ## Language Detection -The Language class allow you to detect a user's language. +The Language class allows you to detect a user's language. ### Usage ```php -use Browser\Language; +use Sinergi\BrowserDetector\Language; + +$language = new Language(); -$language = new Language; -if ($language->getLanguage() == 'de') { - echo 'Get this website in german.'; +if ($language->getLanguage() === 'de') { + echo 'Get this website in german.'; } ``` + +## License + +PHP Browser is licensed under [The MIT License (MIT)](LICENSE). diff --git a/composer.json b/composer.json index 80487de..71a062a 100644 --- a/composer.json +++ b/composer.json @@ -1,9 +1,7 @@ { - "name": "gabrielbull/browser", - "type": "library", + "name": "sinergi/browser-detector", "description": "Detecting the user's browser, operating system and language.", "keywords": ["browser", "os", "operating system", "language", "detection"], - "homepage": "https://github.com/gabrielbull/php-browser", "license": "MIT", "authors": [ { @@ -11,25 +9,25 @@ "email": "me@gabrielbull.com" }, { - "name": "Chris Schuld", - "email": "chris@chrisschuld.com", - "homepage": "http://chrisschuld.com/" + "name": "Chris Schuld" } ], "require": { - "php": ">=5.3.0" + "php": ">=7.2" }, "require-dev": { - "phpunit/phpunit": "~4" + "phpunit/phpunit": "^8.0 || ^9.4" }, "autoload": { "psr-4": { - "Browser\\": "src/Browser" + "Sinergi\\BrowserDetector\\": "src" } }, "autoload-dev": { "psr-4": { - "Browser\\Tests\\": ["tests/Browser/Tests", "tests/Browser/Tests/_includes"] + "Sinergi\\BrowserDetector\\Tests\\": ["tests/BrowserDetector/Tests", "tests/BrowserDetector/Tests/_includes"] } - } + }, + "minimum-stability": "dev", + "prefer-stable": true } diff --git a/phpunit.xml.dist b/phpunit.xml.dist index 9b948f9..b76d52d 100644 --- a/phpunit.xml.dist +++ b/phpunit.xml.dist @@ -1,15 +1,18 @@ - + + + + + ./src + + - - ./tests/Browser/ + + ./tests diff --git a/ruleset.xml b/ruleset.xml new file mode 100644 index 0000000..8931046 --- /dev/null +++ b/ruleset.xml @@ -0,0 +1,187 @@ + + + The PSR-2 coding standard. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 0 + + + 0 + + + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 0 + + + + + + + + + + + + + + + + + + + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/Browser/AcceptLanguage.php b/src/AcceptLanguage.php similarity index 96% rename from src/Browser/AcceptLanguage.php rename to src/AcceptLanguage.php index af921c0..871100e 100644 --- a/src/Browser/AcceptLanguage.php +++ b/src/AcceptLanguage.php @@ -1,5 +1,6 @@ acceptLanguageString = $acceptLanguageString; + return $this; } @@ -36,6 +39,7 @@ public function getAcceptLanguageString() if (null === $this->acceptLanguageString) { $this->createAcceptLanguageString(); } + return $this->acceptLanguageString; } @@ -46,6 +50,7 @@ public function createAcceptLanguageString() { $acceptLanguageString = isset($_SERVER['HTTP_ACCEPT_LANGUAGE']) ? $_SERVER['HTTP_ACCEPT_LANGUAGE'] : null; $this->setAcceptLanguageString($acceptLanguageString); + return $acceptLanguageString; } } diff --git a/src/Browser/Browser.php b/src/Browser.php similarity index 67% rename from src/Browser/Browser.php rename to src/Browser.php index 73d6b01..2e34aca 100644 --- a/src/Browser/Browser.php +++ b/src/Browser.php @@ -1,16 +1,14 @@ setUserAgent(new UserAgent($userAgent)); } else { - throw new InvalidArgumentException; + throw new InvalidArgumentException(); } } @@ -89,11 +104,13 @@ public function __construct($userAgent = null) * Set the name of the OS. * * @param string $name + * * @return $this */ public function setName($name) { - $this->name = $name; + $this->name = (string)$name; + return $this; } @@ -107,13 +124,15 @@ public function getName() if (!isset($this->name)) { BrowserDetector::detect($this, $this->getUserAgent()); } + return $this->name; } /** - * Check to see if the specific browser is valid + * Check to see if the specific browser is valid. * * @param string $name + * * @return bool */ public function isBrowser($name) @@ -122,14 +141,16 @@ public function isBrowser($name) } /** - * Set the version of the browser + * Set the version of the browser. * * @param string $version + * * @return $this */ public function setVersion($version) { - $this->version = $version; + $this->version = (string)$version; + return $this; } @@ -143,18 +164,21 @@ public function getVersion() if (!isset($this->name)) { BrowserDetector::detect($this, $this->getUserAgent()); } - return $this->version; + + return (string) $this->version; } /** - * Set the Browser to be a robot + * Set the Browser to be a robot. * * @param bool $isRobot + * * @return $this */ public function setIsRobot($isRobot) { $this->isRobot = (bool)$isRobot; + return $this; } @@ -168,6 +192,7 @@ public function getIsRobot() if (!isset($this->name)) { BrowserDetector::detect($this, $this->getUserAgent()); } + return $this->isRobot; } @@ -181,16 +206,18 @@ public function isRobot() /** * @param bool $isChromeFrame + * * @return $this */ public function setIsChromeFrame($isChromeFrame) { $this->isChromeFrame = (bool)$isChromeFrame; + return $this; } /** - * Used to determine if the browser is actually "chromeframe" + * Used to determine if the browser is actually "chromeframe". * * @return bool */ @@ -199,6 +226,7 @@ public function getIsChromeFrame() if (!isset($this->name)) { BrowserDetector::detect($this, $this->getUserAgent()); } + return $this->isChromeFrame; } @@ -210,13 +238,49 @@ public function isChromeFrame() return $this->getIsChromeFrame(); } + /** + * @param bool $isFacebookWebView + * + * @return $this + */ + public function setIsFacebookWebView($isFacebookWebView) + { + $this->isFacebookWebView = (bool) $isFacebookWebView; + + return $this; + } + + /** + * Used to determine if the browser is actually "facebook". + * + * @return bool + */ + public function getIsFacebookWebView() + { + if (!isset($this->name)) { + BrowserDetector::detect($this, $this->getUserAgent()); + } + + return $this->isFacebookWebView; + } + + /** + * @return bool + */ + public function isFacebookWebView() + { + return $this->getIsFacebookWebView(); + } + /** * @param UserAgent $userAgent + * * @return $this */ public function setUserAgent(UserAgent $userAgent) { $this->userAgent = $userAgent; + return $this; } @@ -227,4 +291,32 @@ public function getUserAgent() { return $this->userAgent; } + + /** + * @param bool + * + * @return $this + */ + public function setIsCompatibilityMode($isCompatibilityMode) + { + $this->isCompatibilityMode = $isCompatibilityMode; + + return $this; + } + + /** + * @return bool + */ + public function isCompatibilityMode() + { + return $this->isCompatibilityMode; + } + + /** + * Render pages outside of IE's compatibility mode. + */ + public function endCompatibilityMode() + { + header('X-UA-Compatible: IE=edge'); + } } diff --git a/src/Browser/BrowserDetector.php b/src/Browser/BrowserDetector.php deleted file mode 100644 index d6b8563..0000000 --- a/src/Browser/BrowserDetector.php +++ /dev/null @@ -1,650 +0,0 @@ -setName($browser::UNKNOWN); - $browser->setVersion($browser::VERSION_UNKNOWN); - - self::checkChromeFrame($browser, $userAgent); - - return ( - // well-known, well-used - // Special Notes: - // (1) Opera must be checked before FireFox due to the odd - // user agents used in some older versions of Opera - // (2) WebTV is strapped onto Internet Explorer so we must - // check for WebTV before IE - // (3) Because of Internet Explorer 11 using - // "Mozilla/5.0 ([...] Trident/7.0; rv:11.0) like Gecko" - // as user agent, tests for IE must be run before any - // tests checking for "Mozilla" - // (4) (deprecated) Galeon is based on Firefox and needs to be - // tested before Firefox is tested - // (5) OmniWeb is based on Safari so OmniWeb check must occur - // before Safari - // (6) Netscape 9+ is based on Firefox so Netscape checks - // before FireFox are necessary - self::checkBrowserWebTv($browser, $userAgent) || - self::checkBrowserInternetExplorer($browser, $userAgent) || - self::checkBrowserOpera($browser, $userAgent) || - self::checkBrowserGaleon($browser, $userAgent) || - self::checkBrowserNetscapeNavigator9Plus($browser, $userAgent) || - self::checkBrowserSeaMonkey($browser, $userAgent) || - self::checkBrowserFirefox($browser, $userAgent) || - self::checkBrowserChrome($browser, $userAgent) || - self::checkBrowserOmniWeb($browser, $userAgent) || - - // common mobile - self::checkBrowserAndroid($browser, $userAgent) || - self::checkBrowserBlackBerry($browser, $userAgent) || - self::checkBrowserNokia($browser, $userAgent) || - - // common bots - self::checkBrowserRobot($browser, $userAgent) || - - // WebKit base check (post mobile and others) - self::checkBrowserSafari($browser, $userAgent) || - - // everyone else - self::checkBrowserNetPositive($browser, $userAgent) || - self::checkBrowserFirebird($browser, $userAgent) || - self::checkBrowserKonqueror($browser, $userAgent) || - self::checkBrowserIcab($browser, $userAgent) || - self::checkBrowserPhoenix($browser, $userAgent) || - self::checkBrowserAmaya($browser, $userAgent) || - self::checkBrowserLynx($browser, $userAgent) || - self::checkBrowserShiretoko($browser, $userAgent) || - self::checkBrowserIceCat($browser, $userAgent) || - self::checkBrowserIceweasel($browser, $userAgent) || - self::checkBrowserMozilla($browser, $userAgent) /* Mozilla is such an open standard that you must check it last */ - ); - } - - /** - * Determine if the user is using Chrome Frame. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkChromeFrame(Browser $browser, UserAgent $userAgent) - { - if (strpos($userAgent->getUserAgentString(), "chromeframe") !== false) { - $browser->setIsChromeFrame(true); - return true; - } - return false; - } - - /** - * Determine if the user is using a BlackBerry. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserBlackBerry(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'blackberry') !== false) { - $aresult = explode("/", stristr($userAgent->getUserAgentString(), "BlackBerry")); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - $browser->setName($browser::BLACKBERRY); - return true; - } - return false; - } - - /** - * Determine if the browser is a robot. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserRobot(Browser $browser, UserAgent $userAgent) - { - if ( - stripos($userAgent->getUserAgentString(), 'bot') !== false || - stripos($userAgent->getUserAgentString(), 'spider') !== false || - stripos($userAgent->getUserAgentString(), 'crawler') !== false - ) { - $browser->setIsRobot(true); - return true; - } - return false; - } - - /** - * Determine if the browser is Internet Explorer. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserInternetExplorer(Browser $browser, UserAgent $userAgent) - { - // Test for v1 - v1.5 IE - if (stripos($userAgent->getUserAgentString(), 'microsoft internet explorer') !== false) { - $browser->setName($browser::IE); - $browser->setVersion('1.0'); - $aresult = stristr($userAgent->getUserAgentString(), '/'); - if (preg_match('/308|425|426|474|0b1/i', $aresult)) { - $browser->setVersion('1.5'); - } - return true; - } // Test for versions > 1.5 and < 11 - else if (stripos($userAgent->getUserAgentString(), 'msie') !== false && stripos($userAgent->getUserAgentString(), 'opera') === false) { - // See if the browser is the odd MSN Explorer - if (stripos($userAgent->getUserAgentString(), 'msnb') !== false) { - $aresult = explode(' ', stristr(str_replace(';', '; ', $userAgent->getUserAgentString()), 'MSN')); - $browser->setName($browser::MSN); - $browser->setVersion(str_replace(array('(', ')', ';'), '', $aresult[1])); - return true; - } - $aresult = explode(' ', stristr(str_replace(';', '; ', $userAgent->getUserAgentString()), 'msie')); - $browser->setName($browser::IE); - $browser->setVersion(str_replace(array('(', ')', ';'), '', $aresult[1])); - return true; - } // Test for versions >= 11 - else if (stripos($userAgent->getUserAgentString(), 'trident') !== false) { - $browser->setName($browser::IE); - - preg_match('/rv:(\d+\.\d+)/', $userAgent->getUserAgentString(), $matches); - if (isset($matches[1])) { - $browser->setVersion($matches[1]); - return true; - } else { - return false; - } - } // Test for Pocket IE - else if (stripos($userAgent->getUserAgentString(), 'mspie') !== false || stripos($userAgent->getUserAgentString(), 'pocket') !== false) { - $aresult = explode(' ', stristr($userAgent->getUserAgentString(), 'mspie')); - $browser->setName($browser::POCKET_IE); - - if (stripos($userAgent->getUserAgentString(), 'mspie') !== false) { - $browser->setVersion($aresult[1]); - } else { - $aversion = explode('/', $userAgent->getUserAgentString()); - $browser->setVersion($aversion[1]); - } - return true; - } - return false; - } - - /** - * Determine if the browser is Opera. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserOpera(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'opera mini') !== false) { - $resultant = stristr($userAgent->getUserAgentString(), 'opera mini'); - if (preg_match('/\//', $resultant)) { - $aresult = explode('/', $resultant); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - } else { - $aversion = explode(' ', stristr($resultant, 'opera mini')); - $browser->setVersion($aversion[1]); - } - $browser->setName($browser::OPERA_MINI); - return true; - } elseif (stripos($userAgent->getUserAgentString(), 'opera') !== false) { - $resultant = stristr($userAgent->getUserAgentString(), 'opera'); - if (preg_match('/Version\/(10.*)$/', $resultant, $matches)) { - $browser->setVersion($matches[1]); - } elseif (preg_match('/\//', $resultant)) { - $aresult = explode('/', str_replace("(", " ", $resultant)); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - } else { - $aversion = explode(' ', stristr($resultant, 'opera')); - $browser->setVersion(isset($aversion[1]) ? $aversion[1] : ""); - } - $browser->setName($browser::OPERA); - return true; - } elseif (stripos($userAgent->getUserAgentString(), ' OPR/') !== false) { - $browser->setName($browser::OPERA); - if (preg_match('/OPR\/([\d\.]*)/', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - } - return true; - } - return false; - } - - /** - * Determine if the browser is Chrome. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserChrome(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Chrome') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'Chrome')); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - $browser->setName($browser::CHROME); - return true; - } - return false; - } - - /** - * Determine if the browser is WebTv. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserWebTv(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'webtv') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'webtv')); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - $browser->setName($browser::WEBTV); - return true; - } - return false; - } - - /** - * Determine if the browser is NetPositive. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserNetPositive(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'NetPositive') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'NetPositive')); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion(str_replace(array('(', ')', ';'), '', $aversion[0])); - $browser->setName($browser::NETPOSITIVE); - return true; - } - return false; - } - - /** - * Determine if the browser is Galeon. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserGaleon(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'galeon') !== false) { - $aresult = explode(' ', stristr($userAgent->getUserAgentString(), 'galeon')); - $aversion = explode('/', $aresult[0]); - $browser->setVersion($aversion[1]); - $browser->setName($browser::GALEON); - return true; - } - return false; - } - - /** - * Determine if the browser is Konqueror. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserKonqueror(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Konqueror') !== false) { - $aresult = explode(' ', stristr($userAgent->getUserAgentString(), 'Konqueror')); - $aversion = explode('/', $aresult[0]); - $browser->setVersion($aversion[1]); - $browser->setName($browser::KONQUEROR); - return true; - } - return false; - } - - /** - * Determine if the browser is iCab. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserIcab(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'icab') !== false) { - $aversion = explode(' ', stristr(str_replace('/', ' ', $userAgent->getUserAgentString()), 'icab')); - $browser->setVersion($aversion[1]); - $browser->setName($browser::ICAB); - return true; - } - return false; - } - - /** - * Determine if the browser is OmniWeb. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserOmniWeb(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'omniweb') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'omniweb')); - $aversion = explode(' ', isset($aresult[1]) ? $aresult[1] : ""); - $browser->setVersion($aversion[0]); - $browser->setName($browser::OMNIWEB); - return true; - } - return false; - } - - /** - * Determine if the browser is Phoenix. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserPhoenix(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Phoenix') !== false) { - $aversion = explode('/', stristr($userAgent->getUserAgentString(), 'Phoenix')); - $browser->setVersion($aversion[1]); - $browser->setName($browser::PHOENIX); - return true; - } - return false; - } - - /** - * Determine if the browser is Firebird. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserFirebird(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Firebird') !== false) { - $aversion = explode('/', stristr($userAgent->getUserAgentString(), 'Firebird')); - $browser->setVersion($aversion[1]); - $browser->setName($browser::FIREBIRD); - return true; - } - return false; - } - - /** - * Determine if the browser is Netscape Navigator 9+. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserNetscapeNavigator9Plus(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Firefox') !== false && preg_match('/Navigator\/([^ ]*)/i', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::NETSCAPE_NAVIGATOR); - return true; - } elseif (stripos($userAgent->getUserAgentString(), 'Firefox') === false && preg_match('/Netscape6?\/([^ ]*)/i', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::NETSCAPE_NAVIGATOR); - return true; - } - return false; - } - - /** - * Determine if the browser is Shiretoko. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserShiretoko(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Mozilla') !== false && preg_match('/Shiretoko\/([^ ]*)/i', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::SHIRETOKO); - return true; - } - return false; - } - - /** - * Determine if the browser is Ice Cat. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserIceCat(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Mozilla') !== false && preg_match('/IceCat\/([^ ]*)/i', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::ICECAT); - return true; - } - return false; - } - - /** - * Determine if the browser is Nokia. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserNokia(Browser $browser, UserAgent $userAgent) - { - if (preg_match("/Nokia([^\/]+)\/([^ SP]+)/i", $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[2]); - if (stripos($userAgent->getUserAgentString(), 'Series60') !== false || strpos($userAgent->getUserAgentString(), 'S60') !== false) { - $browser->setName($browser::NOKIA_S60); - } else { - $browser->setName($browser::NOKIA); - } - return true; - } - return false; - } - - /** - * Determine if the browser is Firefox. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserFirefox(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'safari') === false) { - if (preg_match("/Firefox[\/ \(]([^ ;\)]+)/i", $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::FIREFOX); - return true; - } elseif (preg_match("/Firefox$/i", $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion(""); - $browser->setName($browser::FIREFOX); - return true; - } - } - return false; - } - - /** - * Determine if the browser is SeaMonkey. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserSeaMonkey(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'safari') === false) { - if (preg_match("/SeaMonkey[\/ \(]([^ ;\)]+)/i", $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - $browser->setName($browser::SEAMONKEY); - return true; - } elseif (preg_match("/SeaMonkey$/i", $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion(""); - $browser->setName($browser::SEAMONKEY); - return true; - } - } - return false; - } - - /** - * Determine if the browser is Iceweasel. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserIceweasel(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Iceweasel') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'Iceweasel')); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - $browser->setName($browser::ICEWEASEL); - return true; - } - return false; - } - - /** - * Determine if the browser is Mozilla. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserMozilla(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'mozilla') !== false && preg_match('/rv:[0-9].[0-9][a-b]?/i', $userAgent->getUserAgentString()) && stripos($userAgent->getUserAgentString(), 'netscape') === false) { - $aversion = explode(' ', stristr($userAgent->getUserAgentString(), 'rv:')); - preg_match('/rv:[0-9].[0-9][a-b]?/i', $userAgent->getUserAgentString(), $aversion); - $browser->setVersion(str_replace('rv:', '', $aversion[0])); - $browser->setName($browser::MOZILLA); - return true; - } elseif (stripos($userAgent->getUserAgentString(), 'mozilla') !== false && preg_match('/rv:[0-9]\.[0-9]/i', $userAgent->getUserAgentString()) && stripos($userAgent->getUserAgentString(), 'netscape') === false) { - $aversion = explode('', stristr($userAgent->getUserAgentString(), 'rv:')); - $browser->setVersion(str_replace('rv:', '', $aversion[0])); - $browser->setName($browser::MOZILLA); - return true; - } elseif (stripos($userAgent->getUserAgentString(), 'mozilla') !== false && preg_match('/mozilla\/([^ ]*)/i', $userAgent->getUserAgentString(), $matches) && stripos($userAgent->getUserAgentString(), 'netscape') === false) { - $browser->setVersion($matches[1]); - $browser->setName($browser::MOZILLA); - return true; - } - return false; - } - - /** - * Determine if the browser is Lynx. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserLynx(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'lynx') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'Lynx')); - $aversion = explode(' ', (isset($aresult[1]) ? $aresult[1] : "")); - $browser->setVersion($aversion[0]); - $browser->setName($browser::LYNX); - return true; - } - return false; - } - - /** - * Determine if the browser is Amaya. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserAmaya(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'amaya') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'Amaya')); - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - $browser->setName($browser::AMAYA); - return true; - } - return false; - } - - /** - * Determine if the browser is Safari. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserSafari(Browser $browser, UserAgent $userAgent) - { - if (stripos($userAgent->getUserAgentString(), 'Safari') !== false) { - $aresult = explode('/', stristr($userAgent->getUserAgentString(), 'Version')); - if (isset($aresult[1])) { - $aversion = explode(' ', $aresult[1]); - $browser->setVersion($aversion[0]); - } else { - $browser->setVersion($browser::VERSION_UNKNOWN); - } - $browser->setName($browser::SAFARI); - return true; - } - return false; - } - - /** - * Determine if the browser is Android. - * - * @param Browser $browser - * @param UserAgent $userAgent - * @return bool - */ - private static function checkBrowserAndroid(Browser $browser, UserAgent $userAgent) - { - // Navigator - if (stripos($userAgent->getUserAgentString(), 'Android') !== false) { - if (preg_match('/Version\/([\d\.]*)/i', $userAgent->getUserAgentString(), $matches)) { - $browser->setVersion($matches[1]); - } else { - $browser->setVersion($browser::VERSION_UNKNOWN); - } - $browser->setName($browser::NAVIGATOR); - return true; - } - return false; - } -} diff --git a/src/Browser/Device.php b/src/Browser/Device.php deleted file mode 100644 index 5087db5..0000000 --- a/src/Browser/Device.php +++ /dev/null @@ -1,83 +0,0 @@ -isDetected) { - $detector = (new DeviceDetector()); - $detector->detect($this); - } - return $this->name; - } - - /** - * @param string $name - * @return $this - */ - public function setName($name) - { - $this->name = $name; - return $this; - } - - /** - * @return string - */ - public function getVersion() - { - return $this->version; - } - - /** - * @param string $version - * @return $this - */ - public function setVersion($version) - { - $this->version = $version; - return $this; - } - - /** - * @return boolean - */ - public function isDetected() - { - return $this->isDetected; - } - - /** - * @param boolean $isDetected - * @return $this - */ - public function setIsDetected($isDetected) - { - $this->isDetected = $isDetected; - return $this; - } -} diff --git a/src/Browser/DeviceDetector.php b/src/Browser/DeviceDetector.php deleted file mode 100644 index 0b2c0c9..0000000 --- a/src/Browser/DeviceDetector.php +++ /dev/null @@ -1,89 +0,0 @@ -device = $device; - } - - if (!$this->device instanceof Device) { - throw new InvalidArgumentException; - } - - if (!$this->userAgent instanceof UserAgent) { - $this->userAgent = new UserAgent(); - $this->userAgent->createUserAgentString(); - } - - $this->checkIpad(); - - $this->device->setIsDetected(true); - } - - /** - * @return bool - */ - public function checkIpad() - { - if (stripos($this->userAgent->getUserAgentString(), 'ipad') !== false) { - $this->device->setName(Device::IPAD); - return true; - } - return false; - } - - /** - * @return Device - */ - public function getDevice() - { - return $this->device; - } - - /** - * @param Device $device - * @return $this - */ - public function setDevice(Device $device) - { - $this->device = $device; - return $this; - } - - /** - * @return UserAgent - */ - public function getUserAgent() - { - return $this->userAgent; - } - - /** - * @param UserAgent $userAgent - * @return $this - */ - public function setUserAgent(UserAgent $userAgent) - { - $this->userAgent = $userAgent; - return $this; - } -} diff --git a/src/Browser/LanguageDetector.php b/src/Browser/LanguageDetector.php deleted file mode 100644 index 22a14fc..0000000 --- a/src/Browser/LanguageDetector.php +++ /dev/null @@ -1,38 +0,0 @@ -getAcceptLanguageString(); - $languages = array(); - $language->setLanguages($languages); - - if (!empty($acceptLanguageString)) { - $httpLanguages = preg_split('/q=([\d\.]*)/', $acceptLanguageString, -1, PREG_SPLIT_NO_EMPTY | PREG_SPLIT_DELIM_CAPTURE); - - $key = 0; - foreach (array_reverse($httpLanguages) as $value) { - $value = trim($value, ',; .'); - if (is_numeric($value)) { - $key = $value; - } else { - $languages[$key] = explode(',', $value); - } - } - krsort($languages); - - foreach ($languages as $value) { - $language->setLanguages(array_merge($language->getLanguages(), $value)); - } - } - } -} diff --git a/src/BrowserDetector.php b/src/BrowserDetector.php new file mode 100644 index 0000000..62523e5 --- /dev/null +++ b/src/BrowserDetector.php @@ -0,0 +1,1014 @@ +getUserAgent(); + } + self::$userAgentString = $userAgent->getUserAgentString(); + + self::$browser->setName(Browser::UNKNOWN); + self::$browser->setVersion(Browser::VERSION_UNKNOWN); + + self::checkChromeFrame(); + self::checkFacebookWebView(); + + foreach (self::$browsersList as $browserName) { + $funcName = self::FUNC_PREFIX . $browserName; + + if (self::$funcName()) { + return true; + } + } + + return false; + } + + /** + * Determine if the user is using Chrome Frame. + * + * @return bool + */ + public static function checkChromeFrame() + { + if (strpos(self::$userAgentString, 'chromeframe') !== false) { + self::$browser->setIsChromeFrame(true); + + return true; + } + + return false; + } + + /** + * Determine if the user is using Facebook. + * + * @return bool + */ + public static function checkFacebookWebView() + { + if (strpos(self::$userAgentString, 'FBAV') !== false) { + self::$browser->setIsFacebookWebView(true); + + return true; + } + + return false; + } + + /** + * Determine if the user is using a BlackBerry. + * + * @return bool + */ + public static function checkBrowserBlackBerry() + { + if (stripos(self::$userAgentString, 'blackberry') !== false) { + if (stripos(self::$userAgentString, 'Version/') !== false) { + $aresult = explode('Version/', self::$userAgentString); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + } else { + $aresult = explode('/', stristr(self::$userAgentString, 'BlackBerry')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + } + self::$browser->setName(Browser::BLACKBERRY); + + return true; + } elseif (stripos(self::$userAgentString, 'BB10') !== false) { + $aresult = explode('Version/10.', self::$userAgentString); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion('10.' . $aversion[0]); + } + self::$browser->setName(Browser::BLACKBERRY); + return true; + } + + return false; + } + + /** + * Determine if the browser is a robot. + * + * @return bool + */ + public static function checkBrowserRobot() + { + if (stripos(self::$userAgentString, 'bot') !== false || + stripos(self::$userAgentString, 'spider') !== false || + stripos(self::$userAgentString, 'crawler') !== false + ) { + self::$browser->setIsRobot(true); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Internet Explorer. + * + * @return bool + */ + public static function checkBrowserInternetExplorer() + { + // Test for v1 - v1.5 IE + if (stripos(self::$userAgentString, 'microsoft internet explorer') !== false) { + self::$browser->setName(Browser::IE); + self::$browser->setVersion('1.0'); + $aresult = stristr(self::$userAgentString, '/'); + if (preg_match('/308|425|426|474|0b1/i', $aresult)) { + self::$browser->setVersion('1.5'); + } + + return true; + } // Test for versions > 1.5 and < 11 and some cases of 11 + else { + if (stripos(self::$userAgentString, 'msie') !== false && stripos(self::$userAgentString, 'opera') === false + ) { + // See if the browser is the odd MSN Explorer + if (stripos(self::$userAgentString, 'msnb') !== false) { + $aresult = explode(' ', stristr(str_replace(';', '; ', self::$userAgentString), 'MSN')); + self::$browser->setName(Browser::MSN); + if (isset($aresult[1])) { + self::$browser->setVersion(str_replace(array('(', ')', ';'), '', $aresult[1])); + } + + return true; + } + $aresult = explode(' ', stristr(str_replace(';', '; ', self::$userAgentString), 'msie')); + self::$browser->setName(Browser::IE); + if (isset($aresult[1])) { + self::$browser->setVersion(str_replace(array('(', ')', ';'), '', $aresult[1])); + } + // See https://msdn.microsoft.com/en-us/library/ie/hh869301%28v=vs.85%29.aspx + // Might be 11, anyway ! + if (stripos(self::$userAgentString, 'trident') !== false) { + preg_match('/rv:(\d+\.\d+)/', self::$userAgentString, $matches); + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + + // At this poing in the method, we know the MSIE and Trident + // strings are present in the $userAgentString. If we're in + // compatibility mode, we need to determine the true version. + // If the MSIE version is 7.0, we can look at the Trident + // version to *approximate* the true IE version. If we don't + // find a matching pair, ( e.g. MSIE 7.0 && Trident/7.0 ) + // we're *not* in compatibility mode and the browser really + // is version 7.0. + if (stripos(self::$userAgentString, 'MSIE 7.0;')) { + if (stripos(self::$userAgentString, 'Trident/7.0;')) { + // IE11 in compatibility mode + self::$browser->setVersion('11.0'); + self::$browser->setIsCompatibilityMode(true); + } elseif (stripos(self::$userAgentString, 'Trident/6.0;')) { + // IE10 in compatibility mode + self::$browser->setVersion('10.0'); + self::$browser->setIsCompatibilityMode(true); + } elseif (stripos(self::$userAgentString, 'Trident/5.0;')) { + // IE9 in compatibility mode + self::$browser->setVersion('9.0'); + self::$browser->setIsCompatibilityMode(true); + } elseif (stripos(self::$userAgentString, 'Trident/4.0;')) { + // IE8 in compatibility mode + self::$browser->setVersion('8.0'); + self::$browser->setIsCompatibilityMode(true); + } + } + } + + return true; + } // Test for versions >= 11 + else { + if (stripos(self::$userAgentString, 'trident') !== false) { + self::$browser->setName(Browser::IE); + + preg_match('/rv:(\d+\.\d+)/', self::$userAgentString, $matches); + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + + return true; + } else { + return false; + } + } // Test for Pocket IE + else { + if (stripos(self::$userAgentString, 'mspie') !== false || + stripos( + self::$userAgentString, + 'pocket' + ) !== false + ) { + $aresult = explode(' ', stristr(self::$userAgentString, 'mspie')); + self::$browser->setName(Browser::POCKET_IE); + + if (stripos(self::$userAgentString, 'mspie') !== false) { + if (isset($aresult[1])) { + self::$browser->setVersion($aresult[1]); + } + } else { + $aversion = explode('/', self::$userAgentString); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + } + + return true; + } + } + } + } + + return false; + } + + /** + * Determine if the browser is Opera. + * + * @return bool + */ + public static function checkBrowserOpera() + { + if (stripos(self::$userAgentString, 'opera mini') !== false) { + $resultant = stristr(self::$userAgentString, 'opera mini'); + if (preg_match('/\//', $resultant)) { + $aresult = explode('/', $resultant); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + } else { + $aversion = explode(' ', stristr($resultant, 'opera mini')); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + } + self::$browser->setName(Browser::OPERA_MINI); + + return true; + } elseif (stripos(self::$userAgentString, 'OPiOS') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'OPiOS')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::OPERA_MINI); + + return true; + } elseif (stripos(self::$userAgentString, 'opera') !== false) { + $resultant = stristr(self::$userAgentString, 'opera'); + if (preg_match('/Version\/(1[0-2].*)$/', $resultant, $matches)) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + } elseif (preg_match('/\//', $resultant)) { + $aresult = explode('/', str_replace('(', ' ', $resultant)); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + } else { + $aversion = explode(' ', stristr($resultant, 'opera')); + self::$browser->setVersion(isset($aversion[1]) ? $aversion[1] : ''); + } + self::$browser->setName(Browser::OPERA); + + return true; + } elseif (stripos(self::$userAgentString, ' OPR/') !== false) { + self::$browser->setName(Browser::OPERA); + if (preg_match('/OPR\/([\d\.]*)/', self::$userAgentString, $matches)) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + } + + return true; + } + + return false; + } + + /** + * Determine if the browser is Samsung. + * + * @return bool + */ + public static function checkBrowserSamsung() + { + if (stripos(self::$userAgentString, 'SamsungBrowser') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'SamsungBrowser')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::SAMSUNG_BROWSER); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Chrome. + * + * @return bool + */ + public static function checkBrowserChrome() + { + if (stripos(self::$userAgentString, 'Chrome') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Chrome')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::CHROME); + + return true; + } elseif (stripos(self::$userAgentString, 'CriOS') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'CriOS')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::CHROME); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Vivaldi. + * + * @return bool + */ + public static function checkBrowserVivaldi() + { + if (stripos(self::$userAgentString, 'Vivaldi') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Vivaldi')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::VIVALDI); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Microsoft Edge. + * + * @return bool + */ + public static function checkBrowserEdge() + { + if (stripos(self::$userAgentString, 'Edge') !== false) { + $version = explode('Edge/', self::$userAgentString); + if (isset($version[1])) { + self::$browser->setVersion((float)$version[1]); + } + self::$browser->setName(Browser::EDGE); + + return true; + } elseif (stripos(self::$userAgentString, 'Edg') !== false) { + $version = explode('Edg/', self::$userAgentString); + if (isset($version[1])) { + self::$browser->setVersion(trim($version[1])); + } + self::$browser->setName(Browser::EDGE); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Google Search Appliance. + * + * @return bool + */ + public static function checkBrowserGsa() + { + if (stripos(self::$userAgentString, 'GSA') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'GSA')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::GSA); + + return true; + } + + return false; + } + + /** + * Determine if the browser is WebTv. + * + * @return bool + */ + public static function checkBrowserWebTv() + { + if (stripos(self::$userAgentString, 'webtv') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'webtv')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::WEBTV); + + return true; + } + + return false; + } + + /** + * Determine if the browser is NetPositive. + * + * @return bool + */ + public static function checkBrowserNetPositive() + { + if (stripos(self::$userAgentString, 'NetPositive') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'NetPositive')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion(str_replace(array('(', ')', ';'), '', $aversion[0])); + } + self::$browser->setName(Browser::NETPOSITIVE); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Galeon. + * + * @return bool + */ + public static function checkBrowserGaleon() + { + if (stripos(self::$userAgentString, 'galeon') !== false) { + $aresult = explode(' ', stristr(self::$userAgentString, 'galeon')); + $aversion = explode('/', $aresult[0]); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + self::$browser->setName(Browser::GALEON); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Konqueror. + * + * @return bool + */ + public static function checkBrowserKonqueror() + { + if (stripos(self::$userAgentString, 'Konqueror') !== false) { + $aresult = explode(' ', stristr(self::$userAgentString, 'Konqueror')); + $aversion = explode('/', $aresult[0]); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + self::$browser->setName(Browser::KONQUEROR); + + return true; + } + + return false; + } + + /** + * Determine if the browser is iCab. + * + * @return bool + */ + public static function checkBrowserIcab() + { + if (stripos(self::$userAgentString, 'icab') !== false) { + $aversion = explode(' ', stristr(str_replace('/', ' ', self::$userAgentString), 'icab')); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + self::$browser->setName(Browser::ICAB); + + return true; + } + + return false; + } + + /** + * Determine if the browser is OmniWeb. + * + * @return bool + */ + public static function checkBrowserOmniWeb() + { + if (stripos(self::$userAgentString, 'omniweb') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'omniweb')); + $aversion = explode(' ', isset($aresult[1]) ? $aresult[1] : ''); + self::$browser->setVersion($aversion[0]); + self::$browser->setName(Browser::OMNIWEB); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Phoenix. + * + * @return bool + */ + public static function checkBrowserPhoenix() + { + if (stripos(self::$userAgentString, 'Phoenix') !== false) { + $aversion = explode('/', stristr(self::$userAgentString, 'Phoenix')); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + self::$browser->setName(Browser::PHOENIX); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Firebird. + * + * @return bool + */ + public static function checkBrowserFirebird() + { + if (stripos(self::$userAgentString, 'Firebird') !== false) { + $aversion = explode('/', stristr(self::$userAgentString, 'Firebird')); + if (isset($aversion[1])) { + self::$browser->setVersion($aversion[1]); + } + self::$browser->setName(Browser::FIREBIRD); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Netscape Navigator 9+. + * + * @return bool + */ + public static function checkBrowserNetscapeNavigator9Plus() + { + if (stripos(self::$userAgentString, 'Firefox') !== false && + preg_match('/Navigator\/([^ ]*)/i', self::$userAgentString, $matches) + ) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::NETSCAPE_NAVIGATOR); + + return true; + } elseif (stripos(self::$userAgentString, 'Firefox') === false && + preg_match('/Netscape6?\/([^ ]*)/i', self::$userAgentString, $matches) + ) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::NETSCAPE_NAVIGATOR); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Shiretoko. + * + * @return bool + */ + public static function checkBrowserShiretoko() + { + if (stripos(self::$userAgentString, 'Mozilla') !== false && + preg_match('/Shiretoko\/([^ ]*)/i', self::$userAgentString, $matches) + ) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::SHIRETOKO); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Ice Cat. + * + * @return bool + */ + public static function checkBrowserIceCat() + { + if (stripos(self::$userAgentString, 'Mozilla') !== false && + preg_match('/IceCat\/([^ ]*)/i', self::$userAgentString, $matches) + ) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::ICECAT); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Nokia. + * + * @return bool + */ + public static function checkBrowserNokia() + { + if (preg_match("/Nokia([^\/]+)\/([^ SP]+)/i", self::$userAgentString, $matches)) { + self::$browser->setVersion($matches[2]); + if (stripos(self::$userAgentString, 'Series60') !== false || + strpos(self::$userAgentString, 'S60') !== false + ) { + self::$browser->setName(Browser::NOKIA_S60); + } else { + self::$browser->setName(Browser::NOKIA); + } + + return true; + } + + return false; + } + + /** + * Determine if the browser is Firefox. + * + * @return bool + */ + public static function checkBrowserFirefox() + { + if (stripos(self::$userAgentString, 'safari') === false) { + if (preg_match("/Firefox[\/ \(]([^ ;\)]+)/i", self::$userAgentString, $matches)) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::FIREFOX); + + return true; + } elseif (preg_match('/Firefox$/i', self::$userAgentString, $matches)) { + self::$browser->setVersion(''); + self::$browser->setName(Browser::FIREFOX); + + return true; + } + } + + return false; + } + + /** + * Determine if the browser is SeaMonkey. + * + * @return bool + */ + public static function checkBrowserSeaMonkey() + { + if (stripos(self::$userAgentString, 'safari') === false) { + if (preg_match("/SeaMonkey[\/ \(]([^ ;\)]+)/i", self::$userAgentString, $matches)) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::SEAMONKEY); + + return true; + } elseif (preg_match('/SeaMonkey$/i', self::$userAgentString, $matches)) { + self::$browser->setVersion(''); + self::$browser->setName(Browser::SEAMONKEY); + + return true; + } + } + + return false; + } + + /** + * Determine if the browser is Iceweasel. + * + * @return bool + */ + public static function checkBrowserIceweasel() + { + if (stripos(self::$userAgentString, 'Iceweasel') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Iceweasel')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::ICEWEASEL); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Mozilla. + * + * @return bool + */ + public static function checkBrowserMozilla() + { + if (stripos(self::$userAgentString, 'mozilla') !== false && + preg_match('/rv:[0-9].[0-9][a-b]?/i', self::$userAgentString) && + stripos(self::$userAgentString, 'netscape') === false + ) { + $aversion = explode(' ', stristr(self::$userAgentString, 'rv:')); + preg_match('/rv:[0-9].[0-9][a-b]?/i', self::$userAgentString, $aversion); + self::$browser->setVersion(str_replace('rv:', '', $aversion[0])); + self::$browser->setName(Browser::MOZILLA); + + return true; + } elseif (stripos(self::$userAgentString, 'mozilla') !== false && + preg_match('/rv:[0-9]\.[0-9]/i', self::$userAgentString) && + stripos(self::$userAgentString, 'netscape') === false + ) { + $aversion = explode('', stristr(self::$userAgentString, 'rv:')); + self::$browser->setVersion(str_replace('rv:', '', $aversion[0])); + self::$browser->setName(Browser::MOZILLA); + + return true; + } elseif (stripos(self::$userAgentString, 'mozilla') !== false && + preg_match('/mozilla\/([^ ]*)/i', self::$userAgentString, $matches) && + stripos(self::$userAgentString, 'netscape') === false + ) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + self::$browser->setName(Browser::MOZILLA); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Lynx. + * + * @return bool + */ + public static function checkBrowserLynx() + { + if (stripos(self::$userAgentString, 'lynx') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Lynx')); + $aversion = explode(' ', (isset($aresult[1]) ? $aresult[1] : '')); + self::$browser->setVersion($aversion[0]); + self::$browser->setName(Browser::LYNX); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Amaya. + * + * @return bool + */ + public static function checkBrowserAmaya() + { + if (stripos(self::$userAgentString, 'amaya') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Amaya')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::AMAYA); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Safari. + * + * @return bool + */ + public static function checkBrowserWkhtmltopdf() + { + if (stripos(self::$userAgentString, 'wkhtmltopdf') !== false) { + self::$browser->setName(Browser::WKHTMLTOPDF); + return true; + } + + return false; + } + /** + * Determine if the browser is Safari. + * + * @return bool + */ + public static function checkBrowserSafari() + { + if (stripos(self::$userAgentString, 'Safari') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Version')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } else { + self::$browser->setVersion(Browser::VERSION_UNKNOWN); + } + self::$browser->setName(Browser::SAFARI); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Yandex. + * + * @return bool + */ + public static function checkBrowserYandex() + { + if (stripos(self::$userAgentString, 'YaBrowser') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'YaBrowser')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::YANDEX); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Comodo Dragon / Ice Dragon / Chromodo. + * + * @return bool + */ + public static function checkBrowserDragon() + { + if (stripos(self::$userAgentString, 'Dragon') !== false) { + $aresult = explode('/', stristr(self::$userAgentString, 'Dragon')); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + self::$browser->setVersion($aversion[0]); + } + self::$browser->setName(Browser::DRAGON); + + return true; + } + + return false; + } + + /** + * Determine if the browser is Android. + * + * @return bool + */ + public static function checkBrowserAndroid() + { + // Navigator + if (stripos(self::$userAgentString, 'Android') !== false) { + if (preg_match('/Version\/([\d\.]*)/i', self::$userAgentString, $matches)) { + if (isset($matches[1])) { + self::$browser->setVersion($matches[1]); + } + } else { + self::$browser->setVersion(Browser::VERSION_UNKNOWN); + } + self::$browser->setName(Browser::NAVIGATOR); + + return true; + } + + return false; + } +} diff --git a/src/Browser/DetectorInterface.php b/src/DetectorInterface.php similarity index 52% rename from src/Browser/DetectorInterface.php rename to src/DetectorInterface.php index b059a19..d1bcd84 100644 --- a/src/Browser/DetectorInterface.php +++ b/src/DetectorInterface.php @@ -1,5 +1,6 @@ setUserAgent($userAgent); + } elseif (null === $userAgent || is_string($userAgent)) { + $this->setUserAgent(new UserAgent($userAgent)); + } else { + throw new InvalidArgumentException(); + } + } + + /** + * @param UserAgent $userAgent + * + * @return $this + */ + public function setUserAgent(UserAgent $userAgent) + { + $this->userAgent = $userAgent; + + return $this; + } + + /** + * @return UserAgent + */ + public function getUserAgent() + { + return $this->userAgent; + } + + /** + * @return string + */ + public function getName() + { + if (!isset($this->name)) { + DeviceDetector::detect($this, $this->getUserAgent()); + } + + return $this->name; + } + + /** + * @param string $name + * + * @return $this + */ + public function setName($name) + { + $this->name = (string)$name; + + return $this; + } +} diff --git a/src/DeviceDetector.php b/src/DeviceDetector.php new file mode 100644 index 0000000..9df8490 --- /dev/null +++ b/src/DeviceDetector.php @@ -0,0 +1,96 @@ +setName($device::UNKNOWN); + + return ( + self::checkIpad($device, $userAgent) || + self::checkIphone($device, $userAgent) || + self::checkWindowsPhone($device, $userAgent) || + self::checkSamsungPhone($device, $userAgent) + ); + } + + /** + * Determine if the device is iPad. + * + * @param Device $device + * @param UserAgent $userAgent + * @return bool + */ + private static function checkIpad(Device $device, UserAgent $userAgent) + { + if (stripos($userAgent->getUserAgentString(), 'ipad') !== false) { + $device->setName(Device::IPAD); + return true; + } + + return false; + } + + /** + * Determine if the device is iPhone. + * + * @param Device $device + * @param UserAgent $userAgent + * @return bool + */ + private static function checkIphone(Device $device, UserAgent $userAgent) + { + if (stripos($userAgent->getUserAgentString(), 'iphone;') !== false) { + $device->setName(Device::IPHONE); + return true; + } + + return false; + } + + /** + * Determine if the device is Windows Phone. + * + * @param Device $device + * @param UserAgent $userAgent + * @return bool + */ + private static function checkWindowsPhone(Device $device, UserAgent $userAgent) + { + if (stripos($userAgent->getUserAgentString(), 'Windows Phone') !== false) { + if (preg_match('/Microsoft; (Lumia [^)]*)\)/', $userAgent->getUserAgentString(), $matches)) { + $device->setName($matches[1]); + return true; + } + + $device->setName($device::WINDOWS_PHONE); + return true; + } + return false; + } + + /** + * Determine if the device is Windows Phone. + * + * @param Device $device + * @param UserAgent $userAgent + * @return bool + */ + private static function checkSamsungPhone(Device $device, UserAgent $userAgent) + { + if (preg_match('/SAMSUNG SM-([^ ]*)/i', $userAgent->getUserAgentString(), $matches)) { + $device->setName(str_ireplace('SAMSUNG', 'Samsung', $matches[0])); + return true; + } + return false; + } +} diff --git a/src/InvalidArgumentException.php b/src/InvalidArgumentException.php new file mode 100644 index 0000000..83f8ccb --- /dev/null +++ b/src/InvalidArgumentException.php @@ -0,0 +1,7 @@ +setAcceptLanguage(new AcceptLanguage($acceptLanguage)); } else { - throw new InvalidArgumentException; + throw new InvalidArgumentException(); } } /** - * Get all user's languages + * Get all user's languages. * * @return array */ @@ -52,17 +50,19 @@ public function getLanguages() /** * Set languages. * - * @param string $languages + * @param array $languages + * * @return $this */ public function setLanguages($languages) { $this->languages = $languages; + return $this; } /** - * Get a user's language + * Get a user's language. * * @return string */ @@ -76,9 +76,10 @@ public function getLanguage() } /** - * Get a user's language and locale + * Get a user's language and locale. * * @param string $separator + * * @return string */ public function getLanguageLocale($separator = '-') @@ -104,11 +105,13 @@ public function getLanguageLocale($separator = '-') /** * @param AcceptLanguage $acceptLanguage + * * @return $this */ public function setAcceptLanguage(AcceptLanguage $acceptLanguage) { $this->acceptLanguage = $acceptLanguage; + return $this; } diff --git a/src/LanguageDetector.php b/src/LanguageDetector.php new file mode 100644 index 0000000..8f390bc --- /dev/null +++ b/src/LanguageDetector.php @@ -0,0 +1,58 @@ +getAcceptLanguageString(); + $languages = array(); + $language->setLanguages($languages); + + if (!empty($acceptLanguageString)) { + // Split by ranges (en-US,en;q=0.8) and keep priority value (0.8) + $httpLanguages = preg_split( + '/q=([\d\.]*)/', + $acceptLanguageString, + -1, + PREG_SPLIT_NO_EMPTY | PREG_SPLIT_DELIM_CAPTURE + ); + + // Group by priority + $key = 0; + foreach (array_reverse($httpLanguages) as $value) { + $value = trim($value, ',; .'); + if (is_numeric($value)) { + $key = $value; + } elseif ($value) { + $languages[$key] = preg_split('/[^\w-]+/', $value); + } + } + + // Sort by priority + krsort($languages); + + // Flatten array and remove duplicates + $result = []; + foreach ($languages as $values) { + foreach ($values as $value) { + $result[$value] = true; + } + } + + $language->setLanguages(array_keys($result)); + } + } +} diff --git a/src/Browser/Os.php b/src/Os.php similarity index 85% rename from src/Browser/Os.php rename to src/Os.php index af8c12b..ba50ae6 100644 --- a/src/Browser/Os.php +++ b/src/Os.php @@ -1,12 +1,9 @@ setUserAgent(new UserAgent($userAgent)); } else { - throw new InvalidArgumentException; + throw new InvalidArgumentException(); } } @@ -74,6 +74,7 @@ public function getName() if (!isset($this->name)) { OsDetector::detect($this, $this->getUserAgent()); } + return $this->name; } @@ -81,11 +82,13 @@ public function getName() * Set the name of the OS. * * @param string $name + * * @return $this */ public function setName($name) { - $this->name = $name; + $this->name = (string)$name; + return $this; } @@ -97,10 +100,11 @@ public function setName($name) public function getVersion() { if (isset($this->version)) { - return $this->version; + return (string)$this->version; } else { OsDetector::detect($this, $this->getUserAgent()); - return $this->version; + + return (string)$this->version; } } @@ -108,11 +112,13 @@ public function getVersion() * Set the version of the OS. * * @param string $version + * * @return $this */ public function setVersion($version) { - $this->version = $version; + $this->version = (string)$version; + return $this; } @@ -126,6 +132,7 @@ public function getIsMobile() if (!isset($this->name)) { OsDetector::detect($this, $this->getUserAgent()); } + return $this->isMobile; } @@ -138,7 +145,7 @@ public function isMobile() } /** - * Set the Browser to be mobile + * Set the Browser to be mobile. * * @param bool $isMobile */ @@ -149,11 +156,13 @@ public function setIsMobile($isMobile = true) /** * @param UserAgent $userAgent + * * @return $this */ public function setUserAgent(UserAgent $userAgent) { $this->userAgent = $userAgent; + return $this; } diff --git a/src/Browser/OsDetector.php b/src/OsDetector.php similarity index 67% rename from src/Browser/OsDetector.php rename to src/OsDetector.php index 05fcdf9..40b0611 100644 --- a/src/Browser/OsDetector.php +++ b/src/OsDetector.php @@ -1,13 +1,15 @@ getUserAgentString(), 'opera mini') !== false) { $os->setIsMobile(true); } // Set is mobile for Pocket IE - else if (stripos($userAgent->getUserAgentString(), 'mspie') !== false || stripos($userAgent->getUserAgentString(), 'pocket') !== false) { + elseif (stripos($userAgent->getUserAgentString(), 'mspie') !== false || + stripos($userAgent->getUserAgentString(), 'pocket') !== false) { $os->setIsMobile(true); } } @@ -62,18 +69,46 @@ public static function checkMobileBrowsers(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkIOS(Os $os, UserAgent $userAgent) { - if (stripos($userAgent->getUserAgentString(), 'CPU OS') !== false || stripos($userAgent->getUserAgentString(), 'iPhone OS') !== false && stripos($userAgent->getUserAgentString(), 'OS X')) { + if (stripos($userAgent->getUserAgentString(), 'CPU OS') !== false || + stripos($userAgent->getUserAgentString(), 'iPhone OS') !== false && + stripos($userAgent->getUserAgentString(), 'OS X')) { $os->setName($os::IOS); if (preg_match('/CPU( iPhone)? OS ([\d_]*)/i', $userAgent->getUserAgentString(), $matches)) { $os->setVersion(str_replace('_', '.', $matches[2])); } $os->setIsMobile(true); + + return true; + } + + return false; + } + + /** + * Determine if the user's operating system is Chrome OS. + * + * @param Os $os + * @param UserAgent $userAgent + * + * @return bool + */ + private static function checkChromeOs(Os $os, UserAgent $userAgent) + { + if (stripos($userAgent->getUserAgentString(), ' CrOS') !== false || + stripos($userAgent->getUserAgentString(), 'CrOS ') !== false + ) { + $os->setName($os::CHROME_OS); + if (preg_match('/Chrome\/([\d\.]*)/i', $userAgent->getUserAgentString(), $matches)) { + $os->setVersion($matches[1]); + } return true; } + return false; } @@ -82,6 +117,7 @@ private static function checkIOS(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkOSX(Os $os, UserAgent $userAgent) @@ -89,19 +125,23 @@ private static function checkOSX(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'OS X') !== false) { $os->setName($os::OSX); if (preg_match('/OS X ([\d\._]*)/i', $userAgent->getUserAgentString(), $matches)) { - $os->setVersion(str_replace('_', '.', $matches[1])); + if (isset($matches[1])) { + $os->setVersion(str_replace('_', '.', $matches[1])); + } } + return true; } + return false; } - /** * Determine if the user's operating system is Windows. * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkWindows(Os $os, UserAgent $userAgent) @@ -110,32 +150,47 @@ private static function checkWindows(Os $os, UserAgent $userAgent) $os->setName($os::WINDOWS); // Windows version if (preg_match('/Windows NT ([\d\.]*)/i', $userAgent->getUserAgentString(), $matches)) { - switch (str_replace('_', '.', $matches[1])) { - case '6.2': - $os->setVersion('8'); - break; - case '6.1': - $os->setVersion('7'); - break; - case '6.0': - $os->setVersion('Vista'); - break; - case '5.2': - case '5.1': - $os->setVersion('XP'); - break; - case '5.01': - case '5.0': - $os->setVersion('2000'); - break; - case '4.0': - $os->setVersion('NT 4.0'); - break; + if (isset($matches[1])) { + switch (str_replace('_', '.', $matches[1])) { + case '6.3': + $os->setVersion('8.1'); + break; + case '6.2': + $os->setVersion('8'); + break; + case '6.1': + $os->setVersion('7'); + break; + case '6.0': + $os->setVersion('Vista'); + break; + case '5.2': + case '5.1': + $os->setVersion('XP'); + break; + case '5.01': + case '5.0': + $os->setVersion('2000'); + break; + case '4.0': + $os->setVersion('NT 4.0'); + break; + default: + if ((float)$matches[1] >= 10.0) { + $os->setVersion($matches[1]); + } + break; + } } } + return true; } // Windows Me, Windows 98, Windows 95, Windows CE - else if (preg_match('/(Windows 98; Win 9x 4\.90|Windows 98|Windows 95|Windows CE)/i', $userAgent->getUserAgentString(), $matches)) { + elseif (preg_match( + '/(Windows 98; Win 9x 4\.90|Windows 98|Windows 95|Windows CE)/i', + $userAgent->getUserAgentString(), + $matches + )) { $os->setName($os::WINDOWS); switch (strtolower($matches[0])) { case 'windows 98; win 9x 4.90': @@ -151,25 +206,54 @@ private static function checkWindows(Os $os, UserAgent $userAgent) $os->setVersion('CE'); break; } + return true; } return false; } + + /** + * Determine if the user's operating system is Windows Phone. + * + * @param Os $os + * @param UserAgent $userAgent + * + * @return bool + */ + private static function checkWindowsPhone(Os $os, UserAgent $userAgent) + { + if (stripos($userAgent->getUserAgentString(), 'Windows Phone') !== false) { + $os->setIsMobile(true); + $os->setName($os::WINDOWS_PHONE); + // Windows version + if (preg_match('/Windows Phone ([\d\.]*)/i', $userAgent->getUserAgentString(), $matches)) { + if (isset($matches[1])) { + $os->setVersion((float)$matches[1]); + } + } + + return true; + } + return false; + } /** * Determine if the user's operating system is SymbOS. * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkSymbOS(Os $os, UserAgent $userAgent) { if (stripos($userAgent->getUserAgentString(), 'SymbOS') !== false) { $os->setName($os::SYMBOS); + return true; } + return false; } @@ -178,6 +262,7 @@ private static function checkSymbOS(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkLinux(Os $os, UserAgent $userAgent) @@ -185,8 +270,10 @@ private static function checkLinux(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'Linux') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::LINUX); + return true; } + return false; } @@ -195,6 +282,7 @@ private static function checkLinux(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkNokia(Os $os, UserAgent $userAgent) @@ -203,8 +291,10 @@ private static function checkNokia(Os $os, UserAgent $userAgent) $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::NOKIA); $os->setIsMobile(true); + return true; } + return false; } @@ -213,16 +303,39 @@ private static function checkNokia(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkBlackBerry(Os $os, UserAgent $userAgent) { if (stripos($userAgent->getUserAgentString(), 'BlackBerry') !== false) { - $os->setVersion($os::VERSION_UNKNOWN); + if (stripos($userAgent->getUserAgentString(), 'Version/') !== false) { + $aresult = explode('Version/', $userAgent->getUserAgentString()); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + $os->setVersion($aversion[0]); + } + } else { + $os->setVersion($os::VERSION_UNKNOWN); + } + $os->setName($os::BLACKBERRY); + $os->setIsMobile(true); + + return true; + } elseif (stripos($userAgent->getUserAgentString(), 'BB10') !== false) { + $aresult = explode('Version/10.', $userAgent->getUserAgentString()); + if (isset($aresult[1])) { + $aversion = explode(' ', $aresult[1]); + $os->setVersion('10.' . $aversion[0]); + } else { + $os->setVersion('10'); + } $os->setName($os::BLACKBERRY); $os->setIsMobile(true); + return true; } + return false; } @@ -231,20 +344,25 @@ private static function checkBlackBerry(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkAndroid(Os $os, UserAgent $userAgent) { if (stripos($userAgent->getUserAgentString(), 'Android') !== false) { if (preg_match('/Android ([\d\.]*)/i', $userAgent->getUserAgentString(), $matches)) { - $os->setVersion($matches[1]); + if (isset($matches[1])) { + $os->setVersion($matches[1]); + } } else { $os->setVersion($os::VERSION_UNKNOWN); } $os->setName($os::ANDROID); $os->setIsMobile(true); + return true; } + return false; } @@ -253,6 +371,7 @@ private static function checkAndroid(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkFreeBSD(Os $os, UserAgent $userAgent) @@ -260,8 +379,10 @@ private static function checkFreeBSD(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'FreeBSD') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::FREEBSD); + return true; } + return false; } @@ -270,6 +391,7 @@ private static function checkFreeBSD(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkOpenBSD(Os $os, UserAgent $userAgent) @@ -277,8 +399,10 @@ private static function checkOpenBSD(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'OpenBSD') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::OPENBSD); + return true; } + return false; } @@ -287,6 +411,7 @@ private static function checkOpenBSD(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkSunOS(Os $os, UserAgent $userAgent) @@ -294,8 +419,10 @@ private static function checkSunOS(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'SunOS') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::SUNOS); + return true; } + return false; } @@ -304,6 +431,7 @@ private static function checkSunOS(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkNetBSD(Os $os, UserAgent $userAgent) @@ -311,8 +439,10 @@ private static function checkNetBSD(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'NetBSD') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::NETBSD); + return true; } + return false; } @@ -321,6 +451,7 @@ private static function checkNetBSD(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkOpenSolaris(Os $os, UserAgent $userAgent) @@ -328,8 +459,10 @@ private static function checkOpenSolaris(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'OpenSolaris') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::OPENSOLARIS); + return true; } + return false; } @@ -338,6 +471,7 @@ private static function checkOpenSolaris(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkOS2(Os $os, UserAgent $userAgent) @@ -345,8 +479,10 @@ private static function checkOS2(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'OS\/2') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::OS2); + return true; } + return false; } @@ -355,6 +491,7 @@ private static function checkOS2(Os $os, UserAgent $userAgent) * * @param Os $os * @param UserAgent $userAgent + * * @return bool */ private static function checkBeOS(Os $os, UserAgent $userAgent) @@ -362,8 +499,10 @@ private static function checkBeOS(Os $os, UserAgent $userAgent) if (stripos($userAgent->getUserAgentString(), 'BeOS') !== false) { $os->setVersion($os::VERSION_UNKNOWN); $os->setName($os::BEOS); + return true; } + return false; } } diff --git a/src/Browser/UserAgent.php b/src/UserAgent.php similarity index 90% rename from src/Browser/UserAgent.php rename to src/UserAgent.php index 020f3d9..adcec40 100644 --- a/src/Browser/UserAgent.php +++ b/src/UserAgent.php @@ -1,5 +1,6 @@ userAgentString = $userAgentString; + $this->userAgentString = (string)$userAgentString; + return $this; } @@ -36,6 +39,7 @@ public function getUserAgentString() if (null === $this->userAgentString) { $this->createUserAgentString(); } + return $this->userAgentString; } @@ -46,6 +50,7 @@ public function createUserAgentString() { $userAgentString = isset($_SERVER['HTTP_USER_AGENT']) ? $_SERVER['HTTP_USER_AGENT'] : null; $this->setUserAgentString($userAgentString); + return $userAgentString; } } diff --git a/tests/Browser/Tests/AcceptLanguageTest.php b/tests/Browser/Tests/AcceptLanguageTest.php deleted file mode 100644 index 124adf5..0000000 --- a/tests/Browser/Tests/AcceptLanguageTest.php +++ /dev/null @@ -1,20 +0,0 @@ -assertNull($acceptLanguage->getAcceptLanguageString()); - - $acceptLanguage = new AcceptLanguage('my_accept_language_string'); - $this->assertEquals('my_accept_language_string', $acceptLanguage->getAcceptLanguageString()); - - $acceptLanguage->setAcceptLanguageString('my_new_accept_language_string'); - $this->assertEquals('my_new_accept_language_string', $acceptLanguage->getAcceptLanguageString()); - } -} diff --git a/tests/Browser/Tests/BrowserDetectorTest.php b/tests/Browser/Tests/BrowserDetectorTest.php deleted file mode 100644 index ba310b3..0000000 --- a/tests/Browser/Tests/BrowserDetectorTest.php +++ /dev/null @@ -1,18 +0,0 @@ -getString()); - $this->assertEquals($userAgentString->getBrowser(), $browser->getName()); - $this->assertEquals($userAgentString->getBrowserVersion(), $browser->getVersion()); - } - } -} diff --git a/tests/Browser/Tests/BrowserTest.php b/tests/Browser/Tests/BrowserTest.php deleted file mode 100644 index df83981..0000000 --- a/tests/Browser/Tests/BrowserTest.php +++ /dev/null @@ -1,44 +0,0 @@ -assertEquals(Browser::BLACKBERRY, $browser->getName()); - $this->assertEquals('4.5.0.124', $browser->getVersion()); - } - - public function testFirefox() - { - $browser = new Browser("Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0"); - $this->assertEquals(Browser::FIREFOX, $browser->getName()); - $this->assertEquals('18.0', $browser->getVersion()); - } - - public function testInternetExplorer11() - { - $browser = new Browser("Mozilla/5.0 (Windows NT 6.1; WOW64; Trident/7.0; rv:11.0) like Gecko"); - $this->assertEquals(Browser::IE, $browser->getName()); - $this->assertEquals('11.0', $browser->getVersion()); - } - - public function testSeaMonkey() - { - $browser = new Browser("Mozilla/5.0 (Windows; U; Windows NT 5.1; RW; rv:1.8.0.7) Gecko/20110321 MultiZilla/4.33.2.6a SeaMonkey/8.6.55"); - $this->assertEquals(Browser::SEAMONKEY, $browser->getName()); - $this->assertEquals('8.6.55', $browser->getVersion()); - } - - public function testUnknown() - { - $browser = new Browser(); - $this->assertEquals(Browser::UNKNOWN, $browser->getName()); - $this->assertEquals(Browser::VERSION_UNKNOWN, $browser->getVersion()); - } -} diff --git a/tests/Browser/Tests/DeviceDetectorTest.php b/tests/Browser/Tests/DeviceDetectorTest.php deleted file mode 100644 index a9e0ccd..0000000 --- a/tests/Browser/Tests/DeviceDetectorTest.php +++ /dev/null @@ -1,24 +0,0 @@ -setUserAgent(new UserAgent($userAgentString->getString())); - $deviceDetector->detect($device); - - $this->assertEquals($userAgentString->getDevice(), $device->getName()); - $this->assertEquals($userAgentString->getDeviceVersion(), $device->getVersion()); - } -} diff --git a/tests/Browser/Tests/DeviceTest.php b/tests/Browser/Tests/DeviceTest.php deleted file mode 100644 index 8e2d636..0000000 --- a/tests/Browser/Tests/DeviceTest.php +++ /dev/null @@ -1,15 +0,0 @@ -assertEquals(Device::UNKNOWN, $device->getName()); - $this->assertEquals(Device::UNKNOWN_VERSION, $device->getVersion()); - } -} diff --git a/tests/Browser/Tests/LanguageTest.php b/tests/Browser/Tests/LanguageTest.php deleted file mode 100644 index df01e86..0000000 --- a/tests/Browser/Tests/LanguageTest.php +++ /dev/null @@ -1,34 +0,0 @@ -language = new Language($httpAcceptLanguage); - } - - public function testGetLanguage() - { - $this->assertEquals('fr', $this->language->getLanguage()); - } - - public function testGetLanguages() - { - $this->assertGreaterThan(0, sizeof($this->language->getLanguages())); - } - - public function testGetLanguageLocal() - { - $this->assertEquals('fr-CA', $this->language->getLanguageLocale()); - } -} diff --git a/tests/Browser/Tests/OsTest.php b/tests/Browser/Tests/OsTest.php deleted file mode 100644 index 0bdc32b..0000000 --- a/tests/Browser/Tests/OsTest.php +++ /dev/null @@ -1,50 +0,0 @@ -assertEquals(Os::IOS, $os->getName()); - $this->assertEquals('6.0', $os->getVersion()); - } - - public function testOsX() - { - $os = new Os("Mozilla/5.0 (Macintosh; Intel Mac OS X 10_8_2) AppleWebKit/536.26.17 (KHTML, like Gecko) Version/6.0.2 Safari/536.26.17"); - $this->assertEquals(Os::OSX, $os->getName()); - $this->assertEquals('10.8.2', $os->getVersion()); - } - - public function testOsX1010() - { - $os = new Os("Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:34.0) Gecko/20100101 Firefox/34.0"); - $this->assertEquals(Os::OSX, $os->getName()); - $this->assertEquals('10.10', $os->getVersion()); - } - - public function testBlackberry() - { - $os = new Os("Mozilla/5.0 (BlackBerry; U; BlackBerry 9900; en) AppleWebKit/534.11+ (KHTML, like Gecko) Version/7.1.0.346 Mobile Safari/534.11+"); - $this->assertEquals(Os::BLACKBERRY, $os->getName()); - $this->assertEquals(Os::VERSION_UNKNOWN, $os->getVersion()); - } - - public function testIsMobile() - { - $os = new Os("Mozilla/5.0 (iPod; CPU iPhone OS 6_1_3 like Mac OS X) AppleWebKit/536.26 (KHTML, like Gecko) CriOS/28.0.1500.16 Mobile/10B329 Safari/8536.25"); - $this->assertTrue($os->isMobile()); - } - - public function testUnknown() - { - $os = new Os(""); - $this->assertEquals(Os::UNKNOWN, $os->getName()); - $this->assertEquals(Os::VERSION_UNKNOWN, $os->getVersion()); - } -} diff --git a/tests/Browser/Tests/UserAgentTest.php b/tests/Browser/Tests/UserAgentTest.php deleted file mode 100644 index d989e04..0000000 --- a/tests/Browser/Tests/UserAgentTest.php +++ /dev/null @@ -1,20 +0,0 @@ -assertNull($userAgent->getUserAgentString()); - - $userAgent = new UserAgent('my_agent_user_string'); - $this->assertEquals('my_agent_user_string', $userAgent->getUserAgentString()); - - $userAgent->setUserAgentString('my_new_agent_user_string'); - $this->assertEquals('my_new_agent_user_string', $userAgent->getUserAgentString()); - } -} diff --git a/tests/Browser/Tests/_files/UserAgentStrings.xml b/tests/Browser/Tests/_files/UserAgentStrings.xml deleted file mode 100644 index bce861f..0000000 --- a/tests/Browser/Tests/_files/UserAgentStrings.xml +++ /dev/null @@ -1,29 +0,0 @@ - - - - - Opera - 21.0.1432.67 - OS X - 10.9.3 - unknown - unknown - - Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_3) AppleWebKit/537.36 (KHTML, like Gecko) - Chrome/34.0.1847.132 Safari/537.36 OPR/21.0.1432.67 - - - - Safari - 4.0.4 - iOS - 3.2 - iPad - unknown - - Mozilla/5.0(iPad; U; CPU iPhone OS 3_2 like Mac OS X; en-us) AppleWebKit/531.21.10 (KHTML, like Gecko) - Version/4.0.4 Mobile/7B314 Safari/531.21.10gin_lib.cc - - - - diff --git a/tests/BrowserDetector/Tests/AcceptLanguageTest.php b/tests/BrowserDetector/Tests/AcceptLanguageTest.php new file mode 100644 index 0000000..4234b35 --- /dev/null +++ b/tests/BrowserDetector/Tests/AcceptLanguageTest.php @@ -0,0 +1,21 @@ +assertNull($acceptLanguage->getAcceptLanguageString()); + + $acceptLanguage = new AcceptLanguage('my_accept_language_string'); + $this->assertSame('my_accept_language_string', $acceptLanguage->getAcceptLanguageString()); + + $acceptLanguage->setAcceptLanguageString('my_new_accept_language_string'); + $this->assertSame('my_new_accept_language_string', $acceptLanguage->getAcceptLanguageString()); + } +} diff --git a/tests/BrowserDetector/Tests/BrowserDetectorTest.php b/tests/BrowserDetector/Tests/BrowserDetectorTest.php new file mode 100644 index 0000000..07fe46e --- /dev/null +++ b/tests/BrowserDetector/Tests/BrowserDetectorTest.php @@ -0,0 +1,19 @@ +getString()); + $this->assertSame($userAgentString->getBrowser(), $browser->getName()); + $this->assertSame($userAgentString->getBrowserVersion(), $browser->getVersion()); + } + } +} diff --git a/tests/BrowserDetector/Tests/BrowserTest.php b/tests/BrowserDetector/Tests/BrowserTest.php new file mode 100644 index 0000000..59572cc --- /dev/null +++ b/tests/BrowserDetector/Tests/BrowserTest.php @@ -0,0 +1,70 @@ +assertSame(Browser::BLACKBERRY, $browser->getName()); + $this->assertSame('4.5.0.124', $browser->getVersion()); + } + + public function testFirefox() + { + $browser = new Browser('Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0'); + $this->assertSame(Browser::FIREFOX, $browser->getName()); + $this->assertSame('18.0', $browser->getVersion()); + } + + public function testInternetExplorer11() + { + $browser = new Browser('Mozilla/5.0 (Windows NT 6.1; WOW64; Trident/7.0; rv:11.0) like Gecko'); + $this->assertSame(Browser::IE, $browser->getName()); + $this->assertSame('11.0', $browser->getVersion()); + + $browser = new Browser('Mozilla/5.0 (MSIE 9.0; Windows NT 6.3; WOW64; Trident/7.0; rv:11.0) like Gecko'); + $this->assertSame(Browser::IE, $browser->getName()); + $this->assertSame('11.0', $browser->getVersion()); + + $browser = new Browser('Mozilla/5.0 (MSIE 9.0; Windows NT 6.3; WOW64; Trident/7.0;) like Gecko'); + $this->assertSame(Browser::IE, $browser->getName()); + $this->assertSame('9.0', $browser->getVersion()); + } + + public function testSeaMonkey() + { + $browser = new Browser('Mozilla/5.0 (Windows; U; Windows NT 5.1; RW; rv:1.8.0.7) Gecko/20110321 MultiZilla/4.33.2.6a SeaMonkey/8.6.55'); + $this->assertSame(Browser::SEAMONKEY, $browser->getName()); + $this->assertSame('8.6.55', $browser->getVersion()); + } + + public function testUnknown() + { + $browser = new Browser(); + $this->assertSame(Browser::UNKNOWN, $browser->getName()); + $this->assertSame(Browser::VERSION_UNKNOWN, $browser->getVersion()); + } + + public function testFacebookWebview() + { + $browser = new Browser('zilla/5.0 (Linux; Android 4.4.4; One Build/KTU84L.H4) AppleWebKit/537.36 (KHTML, like Gecko) Version/4.0 Chrome/33.0.0.0 Mobile Safari/537.36 [FB_IAB/FB4A;FBAV/28.0.0.20.16;]'); + $this->assertTrue($browser->isFacebookWebview()); + } + + public function testOpera() + { + $browser = new Browser('Opera/9.80 (Windows NT 6.0) Presto/2.12.388 Version/12.14'); + $this->assertSame(Browser::OPERA, $browser->getName()); + $this->assertSame('12.14', $browser->getVersion()); + + $browser = new Browser('Mozilla/5.0 (SunOS 5.8 sun4u; U) Opera 5.0 [en]'); + $this->assertSame(Browser::OPERA, $browser->getName()); + $this->assertSame('5.0', $browser->getVersion()); + } +} diff --git a/tests/BrowserDetector/Tests/DeviceDetectorTest.php b/tests/BrowserDetector/Tests/DeviceDetectorTest.php new file mode 100644 index 0000000..63fced1 --- /dev/null +++ b/tests/BrowserDetector/Tests/DeviceDetectorTest.php @@ -0,0 +1,18 @@ +getString()); + $this->assertSame($userAgentString->getDevice(), $device->getName()); + } + } +} diff --git a/tests/BrowserDetector/Tests/DeviceTest.php b/tests/BrowserDetector/Tests/DeviceTest.php new file mode 100644 index 0000000..4be0b67 --- /dev/null +++ b/tests/BrowserDetector/Tests/DeviceTest.php @@ -0,0 +1,15 @@ +assertSame(Device::UNKNOWN, $device->getName()); + } +} diff --git a/tests/BrowserDetector/Tests/LanguageTest.php b/tests/BrowserDetector/Tests/LanguageTest.php new file mode 100644 index 0000000..c67b6aa --- /dev/null +++ b/tests/BrowserDetector/Tests/LanguageTest.php @@ -0,0 +1,65 @@ +language = new Language($httpAcceptLanguage); + } + + public function testGetLanguage() + { + $this->assertSame('fr', $this->language->getLanguage()); + } + + public function testGetLanguages() + { + $languages = ['fr-CA', 'fr', 'en-CA', 'en', 'en-US']; + $this->assertSame($languages, $this->language->getLanguages()); + } + + public function testGetLanguageLocal() + { + $this->assertSame('fr-CA', $this->language->getLanguageLocale()); + } + + public function testConstructor() + { + $acceptLanguage = new AcceptLanguage('my_accept_language_string'); + $language = new Language($acceptLanguage); + + $this->assertInstanceOf("\\Sinergi\\BrowserDetector\\AcceptLanguage", $acceptLanguage); + $this->assertInstanceOf("\\Sinergi\\BrowserDetector\\Language", $language); + } + + public function testConstructorException() + { + $this->expectException(InvalidArgumentException::class); + new Language(1); + } + + public function testGetLanguageLocale() + { + $language = new Language('ru,en-us;q=0.5,en;q=0.3'); + $this->assertSame('ru', $language->getLanguageLocale()); + } + + public function testGetLanguagesFromBogusHeader() + { + $language = new Language(';q=0.8, de, en;q=0.2, de-CH, de;q=0.4'); + $this->assertSame(['de-CH', 'de', 'en'], $language->getLanguages()); + } +} diff --git a/tests/BrowserDetector/Tests/OsDetectorTest.php b/tests/BrowserDetector/Tests/OsDetectorTest.php new file mode 100644 index 0000000..82a0b39 --- /dev/null +++ b/tests/BrowserDetector/Tests/OsDetectorTest.php @@ -0,0 +1,19 @@ +getString()); + $this->assertSame($userAgentString->getOs(), $os->getName()); + $this->assertSame($userAgentString->getOsVersion(), $os->getVersion()); + } + } +} diff --git a/tests/BrowserDetector/Tests/OsTest.php b/tests/BrowserDetector/Tests/OsTest.php new file mode 100644 index 0000000..a09e4ad --- /dev/null +++ b/tests/BrowserDetector/Tests/OsTest.php @@ -0,0 +1,84 @@ +assertSame(Os::IOS, $os->getName()); + $this->assertSame('6.0', $os->getVersion()); + } + + public function testOsX() + { + $os = new Os('Mozilla/5.0 (Macintosh; Intel Mac OS X 10_8_2) AppleWebKit/536.26.17 (KHTML, like Gecko) Version/6.0.2 Safari/536.26.17'); + $this->assertSame(Os::OSX, $os->getName()); + $this->assertSame('10.8.2', $os->getVersion()); + } + + public function testOsX1010() + { + $os = new Os('Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:34.0) Gecko/20100101 Firefox/34.0'); + $this->assertSame(Os::OSX, $os->getName()); + $this->assertSame('10.10', $os->getVersion()); + } + + public function testBlackberry() + { + $os = new Os('Mozilla/5.0 (BlackBerry; U; BlackBerry 9900; en) AppleWebKit/534.11+ (KHTML, like Gecko) Version/7.1.0.346 Mobile Safari/534.11+'); + $this->assertSame(Os::BLACKBERRY, $os->getName()); + $this->assertSame('7.1.0.346', $os->getVersion()); + } + + public function testIsMobile() + { + $os = new Os('Mozilla/5.0 (Windows Phone 10.0; Android 6.0.1; Microsoft; Lumia 640 LTE) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/51.0.2704.79 Mobile Safari/537.36 Edge/14.14393'); + $this->assertTrue($os->isMobile()); + $os = new Os('Mozilla/5.0 (iPod; CPU iPhone OS 6_1_3 like Mac OS X) AppleWebKit/536.26 (KHTML, like Gecko) CriOS/28.0.1500.16 Mobile/10B329 Safari/8536.25'); + $this->assertTrue($os->isMobile()); + } + + public function testWindows() + { + $os = new Os('Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0)'); + $this->assertSame(Os::WINDOWS, $os->getName()); + $this->assertSame('7', $os->getVersion()); + } + + public function testConstructor() + { + $userAgent = new UserAgent('Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0)'); + $os = new Os($userAgent); + + $this->assertInstanceOf("\\Sinergi\\BrowserDetector\\Os", $os); + } + + public function testConstructorException() + { + $this->expectException(InvalidArgumentException::class); + new Os(1); + } + + public function testGetVersion() + { + $userAgent = new UserAgent('Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0)'); + $os = new Os($userAgent); + + $this->assertSame('7', $os->getVersion()); + } + + public function testUnknown() + { + $os = new Os(''); + $this->assertSame(Os::UNKNOWN, $os->getName()); + $this->assertSame(Os::VERSION_UNKNOWN, $os->getVersion()); + } +} diff --git a/tests/BrowserDetector/Tests/UserAgentTest.php b/tests/BrowserDetector/Tests/UserAgentTest.php new file mode 100644 index 0000000..bd96f68 --- /dev/null +++ b/tests/BrowserDetector/Tests/UserAgentTest.php @@ -0,0 +1,21 @@ +assertEmpty($userAgent->getUserAgentString()); + + $userAgent = new UserAgent('my_agent_user_string'); + $this->assertSame('my_agent_user_string', $userAgent->getUserAgentString()); + + $userAgent->setUserAgentString('my_new_agent_user_string'); + $this->assertSame('my_new_agent_user_string', $userAgent->getUserAgentString()); + } +} diff --git a/tests/BrowserDetector/Tests/_files/UserAgentStrings.xml b/tests/BrowserDetector/Tests/_files/UserAgentStrings.xml new file mode 100644 index 0000000..c7f6bc5 --- /dev/null +++ b/tests/BrowserDetector/Tests/_files/UserAgentStrings.xml @@ -0,0 +1,290 @@ + + + + + Opera + 21.0.1432.67 + OS X + 10.9.3 + unknown + unknown + + Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_3) AppleWebKit/537.36 (KHTML, like Gecko) + Chrome/34.0.1847.132 Safari/537.36 OPR/21.0.1432.67 + + + + Safari + 4.0.4 + iOS + 3.2 + iPad + unknown + + Mozilla/5.0(iPad; U; CPU iPhone OS 3_2 like Mac OS X; en-us) AppleWebKit/531.21.10 (KHTML, like Gecko) + Version/4.0.4 Mobile/7B314 Safari/531.21.10gin_lib.cc + + + + Safari + 8.0 + iOS + 8.1.2 + iPhone + unknown + + Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) + Version/8.0 Mobile/12B440 Safari/600.1.4 + + + + Chrome + 41.0.2272.118 + OS X + 10.10.2 + unknown + unknown + + Mozilla/5.0 (Macintosh; Intel Mac OS X 10_10_2) AppleWebKit/537.36 (KHTML, like Gecko) + Chrome/41.0.2272.118 Safari/537.36 + + + + Yandex + 15.6.2311.3451 + OS X + 10.10.2 + unknown + unknown + + Mozilla/5.0 (Macintosh; Intel Mac OS X 10_10_2) AppleWebKit/537.36 (KHTML, like Gecko) + Chrome/42.0.2311.152 YaBrowser/15.6.2311.3451 (beta) Yowser/2.0 Safari/537.36 + + + + Internet Explorer + 8.0 + Windows + 7 + unknown + unknown + + Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; + .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0) + + + + Firefox + 35.0 + OS X + 10.10 + unknown + unknown + + Mozilla/5.0 (Macintosh; Intel Mac OS X 10.10; rv:35.0) Gecko/20100101 Firefox/35.0 + + + + Opera Mini + 10.1.1.92212 + iOS + 8.1.2 + iPhone + unknown + + Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) + OPiOS/10.1.1.92212 Mobile/12B440 Safari/9537.53 + + + + Chrome + 43.0.2357.51 + iOS + 8.1.2 + iPhone + unknown + + Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) + CriOS/43.0.2357.51 Mobile/12B440 Safari/600.1.4 + + + + Edge + 12.10136 + Windows + 10.0 + unknown + unknown + + Mozilla/5.0 (Windows NT 10.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/42.0.2311.135 Safari/537.36 + Edge/12.10136 + + + + Firefox + 40.0 + Windows + 10.0 + unknown + unknown + + Mozilla/5.0 (Windows NT 10.0; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0 + + + + Vivaldi + 1.0.83.38 + Windows + 7 + unknown + unknown + + Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/40.0.2214.89 Vivaldi/1.0.83.38 Safari/537.36 + + + + Chrome + 47.0.2526.80 + Chrome OS + 47.0.2526.80 + unknown + unknown + + Mozilla/5.0 (X11; CrOS x86_64 7520.62.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/47.0.2526.80 Safari/537.36 + + + + Internet Explorer + 8.0 + Windows + 7 + unknown + unknown + + Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; .NET4.0E) + + + + Internet Explorer + 9.0 + Windows + 7 + unknown + unknown + + Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW64; Trident/5.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; .NET4.0E) + + + + Internet Explorer + 10.0 + Windows + 7 + unknown + unknown + + Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW64; Trident/6.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; .NET4.0E) + + + + Internet Explorer + 11.0 + Windows + 7 + unknown + unknown + + Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW64; Trident/7.0; SLCC2; .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; .NET4.0C; .NET4.0E) + + + + Dragon + 16.1.1.0 + Windows + 8 + unknown + unknown + + Mozilla/5.0 (Windows NT 6.2) AppleWebKit/535.7 (KHTML, like Gecko) Comodo_Dragon/16.1.1.0 Chrome/16.0.912.63 Safari/535.7 + + + + Dragon + 4.1.1.11 + Linux + unknown + unknown + unknown + + Mozilla/5.0 (X11; U; Linux x86_64; en-US) AppleWebKit/532.5 (KHTML, like Gecko) Comodo_Dragon/4.1.1.11 Chrome/4.1.249.1042 Safari/532.5 + + + + BlackBerry + 10.0.9.2372 + BlackBerry + 10.0.9.2372 + unknown + unknown + + Mozilla/5.0 (BB10; Touch) AppleWebKit/537.10+ (KHTML, like Gecko) Version/10.0.9.2372 Mobile Safari/537.10+ + + + + Edge + 14.14393 + Windows Phone + 10 + Lumia 640 LTE + unknown + + Mozilla/5.0 (Windows Phone 10.0; Android 6.0.1; Microsoft; Lumia 640 LTE) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/51.0.2704.79 Mobile Safari/537.36 Edge/14.14393 + + + + BlackBerry + 7.1.0.523 + BlackBerry + 7.1.0.523 + unknown + unknown + + Mozilla/5.0 (BlackBerry; U; BlackBerry 9380; en) AppleWebKit/534.11+ (KHTML, like Gecko) Version/7.1.0.523 Mobile Safari/534.11+ + + + + SamsungBrowser + 3.3 + Android + 5.1.1 + Samsung SM-G360T1 + unknown + + Mozilla/5.0 (Linux; Android 5.1.1; SAMSUNG SM-G360T1 Build/LMY47X) AppleWebKit/537.36 (KHTML, like Gecko) SamsungBrowser/3.3 Chrome/38.0.2125.102 Mobile Safari/537.36 + + + + wkhtmltopdf + unknown + Linux + unknown + unknown + unknown + + Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/534.34 (KHTML, like Gecko) wkhtmltopdf-amd64 Safari/534.34 + + + + Edge + 80.0.361.40 + Windows + 10.0 + unknown + unknown + + Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/80.0.3987.66 + Safari/537.36 Edg/80.0.361.40 + + + + diff --git a/tests/Browser/Tests/_includes/UserAgentString.php b/tests/BrowserDetector/Tests/_includes/UserAgentString.php similarity index 91% rename from tests/Browser/Tests/_includes/UserAgentString.php rename to tests/BrowserDetector/Tests/_includes/UserAgentString.php index 26542ba..919e18e 100644 --- a/tests/Browser/Tests/_includes/UserAgentString.php +++ b/tests/BrowserDetector/Tests/_includes/UserAgentString.php @@ -1,5 +1,6 @@ browser = $browser; + return $this; } @@ -66,29 +69,33 @@ public function getOs() /** * @param string $os + * * @return $this */ public function setOs($os) { $this->os = $os; + return $this; } /** * @return string */ - public function getosVersion() + public function getOsVersion() { - return $this->osVersion; + return (string) $this->osVersion; } /** * @param string $osVersion + * * @return $this */ public function setosVersion($osVersion) { $this->osVersion = $osVersion; + return $this; } @@ -102,11 +109,13 @@ public function getString() /** * @param string $string + * * @return $this */ public function setString($string) { $this->string = $string; + return $this; } @@ -115,16 +124,18 @@ public function setString($string) */ public function getbrowserVersion() { - return $this->browserVersion; + return (string) $this->browserVersion; } /** * @param string $browserVersion + * * @return $this */ public function setbrowserVersion($browserVersion) { $this->browserVersion = $browserVersion; + return $this; } @@ -138,11 +149,13 @@ public function getDevice() /** * @param string $device + * * @return $this */ public function setDevice($device) { $this->device = $device; + return $this; } @@ -156,11 +169,13 @@ public function getDeviceVersion() /** * @param string $deviceVersion + * * @return $this */ public function setDeviceVersion($deviceVersion) { $this->deviceVersion = $deviceVersion; + return $this; } } diff --git a/tests/Browser/Tests/_includes/UserAgentStringMapper.php b/tests/BrowserDetector/Tests/_includes/UserAgentStringMapper.php similarity index 95% rename from tests/Browser/Tests/_includes/UserAgentStringMapper.php rename to tests/BrowserDetector/Tests/_includes/UserAgentStringMapper.php index 6a41153..08ff5e6 100644 --- a/tests/Browser/Tests/_includes/UserAgentStringMapper.php +++ b/tests/BrowserDetector/Tests/_includes/UserAgentStringMapper.php @@ -1,5 +1,6 @@ setString(str_replace(array(PHP_EOL, ' '), ' ', (string)$string[6])); $collection[] = $userAgentString; } + return $collection; } } diff --git a/tests/bootstrap.php b/tests/bootstrap.php index d6627ac..9739040 100644 --- a/tests/bootstrap.php +++ b/tests/bootstrap.php @@ -2,15 +2,15 @@ $vendor = realpath(__DIR__ . '/../vendor'); -if (file_exists($vendor . "/autoload.php")) { - require $vendor . "/autoload.php"; +if (file_exists($vendor . '/autoload.php')) { + require $vendor . '/autoload.php'; } else { $vendor = realpath(__DIR__ . '/../../../'); - if (file_exists($vendor . "/autoload.php")) { - require $vendor . "/autoload.php"; + if (file_exists($vendor . '/autoload.php')) { + require $vendor . '/autoload.php'; } else { - throw new Exception("Unable to load dependencies"); + throw new Exception('Unable to load dependencies'); } } -define('FILES', __DIR__ . "/Browser/Tests/_files"); +define('FILES', __DIR__ . '/BrowserDetector/Tests/_files');