Skip to content

Commit

Permalink
Merge pull request #12 from okonomi/os_version
Browse files Browse the repository at this point in the history
Support parsing OS version
  • Loading branch information
yuya-takeyama committed Oct 26, 2014
2 parents 7f80cfc + d09db0a commit 888c7ab
Show file tree
Hide file tree
Showing 13 changed files with 87 additions and 6 deletions.
3 changes: 3 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,9 @@ $r['os'];

$r['version'];
// => version of browser, or terminal type name of mobile phones

$r['os_version'];
// => version of operating systems (for some typical cases)
```

Parse user-agent string and returns a `array` with keys `name`, `category`, `os`, `version` and `vendor`.
Expand Down
5 changes: 4 additions & 1 deletion scripts/generate_dataset_class.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ function ($element) {
);

file_put_contents(
__DIR__ . '/../src/Woothee/DataSet.php', <<<__SCRIPT__
__DIR__ . '/../src/DataSet.php', <<<__SCRIPT__
<?php
namespace Woothee;
Expand All @@ -34,6 +34,7 @@ class DataSet
const DATASET_KEY_TYPE = 'type';
const DATASET_KEY_CATEGORY = 'category';
const DATASET_KEY_OS = 'os';
const DATASET_KEY_OS_VERSION = 'os_version';
const DATASET_KEY_VENDOR = 'vendor';
const DATASET_KEY_VERSION = 'version';
Expand All @@ -51,6 +52,7 @@ class DataSet
const ATTRIBUTE_NAME = 'name';
const ATTRIBUTE_CATEGORY = 'category';
const ATTRIBUTE_OS = 'os';
const ATTRIBUTE_OS_VERSION = 'os_version';
const ATTRIBUTE_VENDOR = 'vendor';
const ATTRIBUTE_VERSION = 'version';
const VALUE_UNKNOWN = 'UNKNOWN';
Expand All @@ -69,6 +71,7 @@ class DataSet
self::ATTRIBUTE_NAME,
self::ATTRIBUTE_CATEGORY,
self::ATTRIBUTE_OS,
self::ATTRIBUTE_OS_VERSION,
self::ATTRIBUTE_VENDOR,
self::ATTRIBUTE_VERSION,
);
Expand Down
5 changes: 5 additions & 0 deletions src/AgentCategory/AbstractCategory.php
Original file line number Diff line number Diff line change
Expand Up @@ -32,4 +32,9 @@ protected static function updateOs(&$target, $os)
{
$target[DataSet::ATTRIBUTE_OS] = $os;
}

protected static function updateOsVersion(&$target, $os_version)
{
$target[DataSet::ATTRIBUTE_OS_VERSION] = $os_version;
}
}
16 changes: 16 additions & 0 deletions src/AgentCategory/Appliance/Playstation.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,23 +9,39 @@ class Playstation extends AbstractCategory
public static function challenge($ua, &$result)
{
$data = null;
$version = null;

if (strpos($ua, 'PSP (PlayStation Portable);') !== false) {
$data = DataSet::get('PSP');
if (preg_match('/PSP \\(PlayStation Portable\\); ([.0-9]+)\\)/', $ua, $matches) === 1) {
$version = $matches[1];
}
} elseif (strpos($ua, 'PlayStation Vita') !== false) {
$data = DataSet::get('PSVita');
if (preg_match('/PlayStation Vita ([.0-9]+)\\)/', $ua, $matches) === 1) {
$version = $matches[1];
}
} elseif (strpos($ua, 'PLAYSTATION 3 ') !== false
|| strpos($ua, 'PLAYSTATION 3;') !== false) {
$data = DataSet::get('PS3');
if (preg_match('/PLAYSTATION 3;? ([.0-9]+)\\)/', $ua, $matches) === 1) {
$version = $matches[1];
}
} elseif (strpos($ua, 'PlayStation 4 ') !== false) {
$data = DataSet::get('PS4');
if (preg_match('/PlayStation 4 ([.0-9]+)\\)/', $ua, $matches) === 1) {
$version = $matches[1];
}
}

if (is_null($data)) {
return false;
}

static::updateMap($result, $data);
if ($version) {
static::updateOsVersion($result, $version);
}

return true;
}
Expand Down
4 changes: 3 additions & 1 deletion src/AgentCategory/Browser/Msie.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,15 @@ class Msie extends AbstractCategory
{
public static function challenge($ua, &$result)
{
if (strpos($ua, 'compatible; MSIE') !== false || strpos($ua, 'Trident/') !== false) {
if (strpos($ua, 'compatible; MSIE') !== false || strpos($ua, 'Trident/') !== false || strpos($ua, 'IEMobile') !== false) {
$version = DataSet::VALUE_UNKNOWN;

if (preg_match('/MSIE ([.0-9]+);/', $ua, $matches) === 1) {
$version = $matches[1];
} elseif (preg_match('/Trident\/([.0-9]+);(?: BOIE[0-9]+;[A-Z]+;)? rv:([.0-9]+)/', $ua, $matches) === 1) {
$version = $matches[2];
} elseif (preg_match('/IEMobile\/([.0-9]+);/', $ua, $matches) === 1) {
$version = $matches[1];
}

static::updateMap($result, DataSet::get('MSIE'));
Expand Down
7 changes: 7 additions & 0 deletions src/AgentCategory/Os/Linux.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,20 @@ public static function challenge($ua, &$result)
}

$data = DataSet::get('Linux');
$version = null;

if (strpos($ua, 'Android') !== false) {
$data = DataSet::get('Android');
if (preg_match('/Android[- ](\\d+\\.\\d+(?:\\.\\d+)?)/', $ua, $matches)) {
$version = $matches[1];
}
}

static::updateCategory($result, $data[DataSet::DATASET_KEY_CATEGORY]);
static::updateOs($result, $data[DataSet::DATASET_KEY_NAME]);
if ($version) {
static::updateOsVersion($result, $version);
}

return true;
}
Expand Down
14 changes: 14 additions & 0 deletions src/AgentCategory/Os/MiscOs.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,20 +9,34 @@ class MiscOs extends AbstractCategory
public static function challenge($ua, &$result)
{
$data = null;
$os_version = null;

if (strpos($ua, '(Win98;') > -1) {
$data = DataSet::get('Win98');
$os_version = "98";
} elseif (strpos($ua, 'Macintosh; U; PPC;') > -1 || strpos($ua, 'Mac_PowerPC') > -1) {
$data = DataSet::get('MacOS');
if (preg_match('/rv:(\\d+\\.\\d+\\.\\d+)/', $ua, $matches) === 1) {
$os_version = $matches[1];
}
} elseif (strpos($ua, 'X11; FreeBSD ') > -1) {
$data = DataSet::get('BSD');
if (preg_match('/FreeBSD ([^;\\)]+);/', $ua, $matches) === 1) {
$os_version = $matches[1];
}
} elseif (strpos($ua, 'X11; CrOS ') > -1) {
$data = DataSet::get('ChromeOS');
if (preg_match('/CrOS ([^\\)]+)\\)/', $ua, $matches) === 1) {
$os_version = $matches[1];
}
}

if ($data) {
static::updateCategory($result, $data[DataSet::DATASET_KEY_CATEGORY]);
static::updateOs($result, $data[DataSet::DATASET_KEY_NAME]);
if ($os_version) {
static::updateOsVersion($result, $os_version);
}

return true;
}
Expand Down
12 changes: 12 additions & 0 deletions src/AgentCategory/Os/Osx.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ public static function challenge($ua, &$result)
}

$data = DataSet::get('OSX');
$version = null;

if (strpos($ua, 'like Mac OS X') !== false) {
if (strpos($ua, 'iPhone;') !== false) {
Expand All @@ -22,10 +23,21 @@ public static function challenge($ua, &$result)
} elseif (strpos($ua, 'iPod') !== false) {
$data = DataSet::get('iPod');
}

if (preg_match('/; CPU(?: iPhone)? OS (\\d+_\\d+(?:_\\d+)?) like Mac OS X/', $ua, $matches) === 1) {
$version = str_replace('_', '.', $matches[1]);
}
} else {
if (preg_match('/Mac OS X (10[._]\\d+(?:[._]\\d+)?)(?:\\)|;)/', $ua, $matches) === 1) {
$version = str_replace('_', '.', $matches[1]);
}
}

static::updateCategory($result, $data[DataSet::DATASET_KEY_CATEGORY]);
static::updateOs($result, $data[DataSet::DATASET_KEY_NAME]);
if ($version) {
static::updateOsVersion($result, $version);
}

return true;
}
Expand Down
10 changes: 9 additions & 1 deletion src/AgentCategory/Os/SmartPhone.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ class SmartPhone extends AbstractCategory
public static function challenge($ua, &$result)
{
$data = null;
$version = null;

if (strpos($ua, 'iPhone') !== false) {
$data = DataSet::get('iPhone');
Expand All @@ -22,12 +23,16 @@ public static function challenge($ua, &$result)
$data = DataSet::get('iOS');
} elseif (strpos($ua, 'BlackBerry') !== false) {
$data = DataSet::get('BlackBerry');
if (preg_match('/BlackBerry(?:\\d+)\/([.0-9]+) /', $ua, $matches) === 1) {
$version = $matches[1];
}
}

if (isset($result[DataSet::DATASET_KEY_NAME])
&& $result[DataSet::DATASET_KEY_NAME] === 'Firefox') {
if (preg_match('/^Mozilla\/[.0-9]+ \\((Mobile|Tablet);(.*;)? rv:[.0-9]+\\) Gecko\/[.0-9]+ Firefox\/[.0-9]+$/Du', $ua) === 1) {
if (preg_match('/^Mozilla\/[.0-9]+ \\((?:Mobile|Tablet);(?:.*;)? rv:([.0-9]+)\\) Gecko\/[.0-9]+ Firefox\/[.0-9]+$/', $ua, $matches) === 1) {
$data = DataSet::get('FirefoxOS');
$version = $matches[1];
}
}

Expand All @@ -37,6 +42,9 @@ public static function challenge($ua, &$result)

static::updateCategory($result, $data[DataSet::DATASET_KEY_CATEGORY]);
static::updateOs($result, $data[DataSet::DATASET_KEY_NAME]);
if ($version) {
static::updateOsVersion($result, $version);
}

return true;
}
Expand Down
6 changes: 5 additions & 1 deletion src/AgentCategory/Os/Windows.php
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,11 @@ public static function challenge($ua, &$result)
$data = DataSet::get('WinVista');
} elseif ($version === 'NT 5.1') {
$data = DataSet::get('WinXP');
} elseif (strpos($version, 'Phone OS') === 0) {
} elseif (strpos($version, 'Phone') === 0) {
$data = DataSet::get('WinPhone');
if (preg_match('/Phone(?: OS)? ([.0-9]+)/', $ua, $matches) === 1) {
$version = $matches[1];
}
} elseif ($version === 'NT 5.0') {
$data = DataSet::get('Win2000');
} elseif ($version === 'NT 4.0') {
Expand All @@ -62,6 +65,7 @@ public static function challenge($ua, &$result)

static::updateCategory($result, $data[DataSet::DATASET_KEY_CATEGORY]);
static::updateOs($result, $data[DataSet::DATASET_KEY_NAME]);
static::updateOsVersion($result, $version);

return true;
}
Expand Down
5 changes: 4 additions & 1 deletion src/DataSet.php
Original file line number Diff line number Diff line change
@@ -1,14 +1,15 @@
<?php
namespace Woothee;

// GENERATED from dataset.yml at Fri Apr 25 13:36:20 JST 2014 by tagomoris
// GENERATED from dataset.yml at Sun Oct 26 00:45:06 JST 2014 by okonomi
class DataSet
{
const DATASET_KEY_LABEL = 'label';
const DATASET_KEY_NAME = 'name';
const DATASET_KEY_TYPE = 'type';
const DATASET_KEY_CATEGORY = 'category';
const DATASET_KEY_OS = 'os';
const DATASET_KEY_OS_VERSION = 'os_version';
const DATASET_KEY_VENDOR = 'vendor';
const DATASET_KEY_VERSION = 'version';

Expand All @@ -26,6 +27,7 @@ class DataSet
const ATTRIBUTE_NAME = 'name';
const ATTRIBUTE_CATEGORY = 'category';
const ATTRIBUTE_OS = 'os';
const ATTRIBUTE_OS_VERSION = 'os_version';
const ATTRIBUTE_VENDOR = 'vendor';
const ATTRIBUTE_VERSION = 'version';
const VALUE_UNKNOWN = 'UNKNOWN';
Expand All @@ -44,6 +46,7 @@ class DataSet
self::ATTRIBUTE_NAME,
self::ATTRIBUTE_CATEGORY,
self::ATTRIBUTE_OS,
self::ATTRIBUTE_OS_VERSION,
self::ATTRIBUTE_VENDOR,
self::ATTRIBUTE_VERSION,
);
Expand Down
4 changes: 4 additions & 0 deletions tests/Woothee/Tests/ClassifierTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,10 @@ public function testParse($param)
$this->assertSame($expected['os'], $result['os']);
}

if (isset($expected['os_version'])) {
$this->assertSame($expected['os_version'], $result['os_version']);
}

if (isset($expected['version'])) {
$this->assertSame($expected['version'], $result['version']);
}
Expand Down

0 comments on commit 888c7ab

Please sign in to comment.