Skip to content

Commit

Permalink
Accepts String -> List of Formats passing tests. Need to test image/*…
Browse files Browse the repository at this point in the history
… style.
  • Loading branch information
KrisJordan committed May 18, 2009
1 parent 7fdad31 commit d5f5959
Show file tree
Hide file tree
Showing 3 changed files with 152 additions and 33 deletions.
27 changes: 21 additions & 6 deletions recess/recess/http/Accepts.class.php
Expand Up @@ -7,7 +7,8 @@ class Accepts {
protected $headers;

protected $types = false;
protected $typesArray = array();
protected $typesTried = array();
protected $typesCurrent = array();

protected $languages = false;
protected $encodings = false;
Expand All @@ -28,14 +29,25 @@ public function __construct($headers, $overrides = array()) {
public function nextFormat() {
if($this->types === false) { $this->initFormats(); }

while(current($this->typesArray) === false) {
while(current($this->typesCurrent) === false) {
$key = key($this->typesCurrent);

$nextTypes = $this->types->next();
if($nextTypes === false) { return '*'; } // Base case, ran out of types in ACCEPT string
$this->typesArray = MimeType::formatsFor($nextTypes);

if($nextTypes === false) { return false; } // Base case, ran out of types in ACCEPT string
$this->typesTried = array_merge($this->typesTried, $this->typesCurrent);

$nextTypes = MimeType::formatsFor($nextTypes);
$this->typesCurrent = array();
foreach($nextTypes as $type) {
if(!in_array($type, $this->typesTried)) {
$this->typesCurrent[] = $type;
}
}
}

$result = each($this->typesArray);
return $result[1];
$result = each($this->typesCurrent);
return $result[1]; // Each returns an array of (key, value)
}

protected function initFormats() {
Expand All @@ -45,6 +57,9 @@ protected function initFormats() {
public function resetFormats() {
if($this->types !== false)
$this->types->reset();

$this->typesTried = array();
$this->typesCurrent = array();
}

public function nextLanguage() {
Expand Down
109 changes: 87 additions & 22 deletions recess/recess/http/MimeType.class.php
Expand Up @@ -6,36 +6,101 @@ abstract class MimeType {

static function init() {
// TODO: Cache the MIME Type Data Structure
MimeType::registerMany(array(
array('html', 'text/html', array('application/xhtml+xml'), array('xhtml')),
array('xml', 'application/xml', array('text/xml', 'application/x-xml')),
array('json', 'application/json', array('text/x-json','application/jsonrequest')),
array('js', 'text/javascript', array('application/javascript', 'application/x-javascript')),
array('css', 'text/css'),
array('rss', 'application/rss+xml'),
array('atom', 'application/atom+xml'),
array('yaml', 'application/x-yaml', array('text/yaml')),
array('text', 'text/plain', array()),
array('png', 'image/png', array()),
array('jpg', 'image/jpeg', array('image/pjpeg')),
array('gif', 'image/gif', array()),
array('form', 'multipart/form-data'),
array('url-form', 'application/x-www-form-urlencoded'),
array('csv', 'text/csv'),
array('*', '*/*'),
));
MimeType::registerMany(
array(
array('html', array('text/html', 'application/xhtml+xml')),
array('xml', array('application/xml', 'text/xml', 'application/x-xml')),
array('json', array('application/json', 'text/x-json','application/jsonrequest')),
array('js', array('text/javascript', 'application/javascript', 'application/x-javascript')),
array('css', 'text/css'),
array('rss', 'application/rss+xml'),
array('yaml', array('application/x-yaml', 'text/yaml')),
array('atom', 'application/atom+xml'),
array('text', 'text/plain'),
array('png', 'image/png'),
array('jpg', 'image/jpeg', 'image/pjpeg'),
array('gif', 'image/gif'),
array('form', 'multipart/form-data'),
array('url-form', 'application/x-www-form-urlencoded'),
array('csv', 'text/csv'),
)
);
}

static function formatsFor($array) {
return array();
static function formatsFor($types) {
$types = is_array($types) ? $types : array($types);

$linearizedFormats = array();

foreach($types as $type) {
$parts = explode('/', $type);
if(count($parts) >= 1) {
if($parts[0] == '*') {
// Wildcard -- add all formats and return
return self::addUnique($linearizedFormats, array_keys(self::$byFormat));
} else {
if(isset(self::$byMime[$parts[0]])) {
if($parts[1] == '*') {
foreach(self::$byMime[$parts[0]] as $formats) {
$linearizedFormats = self::addUnique($linearizedFormats, $formats);
}
} else {
if(isset(self::$byMime[$parts[0]][$parts[1]])) {
$linearizedFormats = self::addUnique($linearizedFormats, self::$byMime[$parts[0]][$parts[1]]);
}
}
}
}
}
}

if( ($key = array_search('html', $linearizedFormats)) !== false) {
if($key != 0) {
array_splice($linearizedFormats, $key, 1);
array_unshift($linearizedFormats, 'html');
}
}

return $linearizedFormats;
}

static private function addUnique($formats, $additionalFormats) {
foreach($additionalFormats as $format) {
if(!in_array($format, $formats)) $formats[] = $format;
}
return $formats;
}


static function register($type, $extension, $synonyms = array()) {
self::registerMany(array(array($type,$extension,$synonyms)));
}

static function registerMany($array) {

static function registerMany($types) {
foreach($types as $type) {
$formats = is_array($type[0]) ? $type[0] : array($type[0]);
$mimes = is_array($type[1]) ? $type[1] : array($type[1]);

// TODO: Create formats data structure

foreach($mimes as $mime) {
$parts = explode('/', $mime);
if(count($parts) == 2) {
if(!isset(self::$byMime[$parts[0]])) {
self::$byMime[$parts[0]] = array();
}
self::$byMime[$parts[0]][$parts[1]] = $formats;
}
}

foreach($formats as $format) {
if(!isset(self::$byFormat[$format])) {
self::$byFormat[$format] = array();
}
self::$byFormat[$format] = array_unique(array_merge(self::$byFormat[$format], $mimes));

}
}
}

}
Expand Down
49 changes: 44 additions & 5 deletions recess/test/recess/http/AcceptsTest.php
Expand Up @@ -35,22 +35,61 @@ function testChromeContentTypes() {
$this->assertEquals('xml', $this->acceptChrome->nextFormat());
$this->assertEquals('png', $this->acceptChrome->nextFormat());
$this->assertEquals('text', $this->acceptChrome->nextFormat());
$this->assertEquals('*', $this->acceptChrome->nextFormat());

// Now we go down the list of others to expand */*
$this->assertEquals('json', $this->acceptChrome->nextFormat());
$this->assertEquals('js', $this->acceptChrome->nextFormat());
$this->assertEquals('css', $this->acceptChrome->nextFormat());
$this->assertEquals('rss', $this->acceptChrome->nextFormat());
$this->assertEquals('yaml', $this->acceptChrome->nextFormat());
$this->assertEquals('atom', $this->acceptChrome->nextFormat());
$this->assertEquals('jpg', $this->acceptChrome->nextFormat());
$this->assertEquals('gif', $this->acceptChrome->nextFormat());
$this->assertEquals('form', $this->acceptChrome->nextFormat());
$this->assertEquals('url-form', $this->acceptChrome->nextFormat());
$this->assertEquals('csv', $this->acceptChrome->nextFormat());
$this->assertEquals(false, $this->acceptChrome->nextFormat());
}

function testFirefoxContentTypes() {
$this->assertEquals('html', $this->acceptFirefox->nextFormat());
$this->assertEquals('xml', $this->acceptFirefox->nextFormat());
$this->assertEquals('*', $this->acceptFirefox->nextFormat());

// Now we go down the list of others to expand */*
$this->assertEquals('json', $this->acceptFirefox->nextFormat());
$this->assertEquals('js', $this->acceptFirefox->nextFormat());
$this->assertEquals('css', $this->acceptFirefox->nextFormat());
$this->assertEquals('rss', $this->acceptFirefox->nextFormat());
$this->assertEquals('yaml', $this->acceptFirefox->nextFormat());
$this->assertEquals('atom', $this->acceptFirefox->nextFormat());
$this->assertEquals('text', $this->acceptFirefox->nextFormat());
$this->assertEquals('png', $this->acceptFirefox->nextFormat());
$this->assertEquals('jpg', $this->acceptFirefox->nextFormat());
$this->assertEquals('gif', $this->acceptFirefox->nextFormat());
$this->assertEquals('form', $this->acceptFirefox->nextFormat());
$this->assertEquals('url-form', $this->acceptFirefox->nextFormat());
$this->assertEquals('csv', $this->acceptFirefox->nextFormat());
$this->assertEquals(false, $this->acceptFirefox->nextFormat());
}

function testIEContentTypes() {
$this->assertEquals('jpg', $this->acceptIE->nextFormat());
$this->assertEquals('gif', $this->acceptIE->nextFormat());
$this->assertEquals('*', $this->acceptIE->nextFormat());
$this->assertEquals(false, $this->acceptIE->nextFormat());
$this->assertEquals('jpg', $this->acceptIE->nextFormat());

// Now we go down the list of others to expand */*
$this->assertEquals('html', $this->acceptIE->nextFormat());
$this->assertEquals('xml', $this->acceptIE->nextFormat());
$this->assertEquals('json', $this->acceptIE->nextFormat());
$this->assertEquals('js', $this->acceptIE->nextFormat());
$this->assertEquals('css', $this->acceptIE->nextFormat());
$this->assertEquals('rss', $this->acceptIE->nextFormat());
$this->assertEquals('yaml', $this->acceptIE->nextFormat());
$this->assertEquals('atom', $this->acceptIE->nextFormat());
$this->assertEquals('text', $this->acceptIE->nextFormat());
$this->assertEquals('png', $this->acceptIE->nextFormat());
$this->assertEquals('form', $this->acceptIE->nextFormat());
$this->assertEquals('url-form', $this->acceptIE->nextFormat());
$this->assertEquals('csv', $this->acceptIE->nextFormat());
}
}
?>

0 comments on commit d5f5959

Please sign in to comment.