diff --git a/actions/attachment.php b/actions/attachment.php index d9cacb1193..94ccf098e0 100644 --- a/actions/attachment.php +++ b/actions/attachment.php @@ -27,11 +27,7 @@ * @link http://status.net/ */ -if (!defined('STATUSNET') && !defined('LACONICA')) { - exit(1); -} - -require_once INSTALLDIR.'/lib/attachmentlist.php'; +if (!defined('GNUSOCIAL')) { exit(1); } /** * Show notice attachments @@ -42,7 +38,7 @@ require_once INSTALLDIR.'/lib/attachmentlist.php'; * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 * @link http://status.net/ */ -class AttachmentAction extends Action +class AttachmentAction extends ManagedAction { /** * Attachment object to show @@ -68,7 +64,7 @@ class AttachmentAction extends Action $this->attachment = File::getKV($id); } - if (empty($this->attachment)) { + if (!$this->attachment instanceof File) { // TRANS: Client error displayed trying to get a non-existing attachment. $this->clientError(_('No such attachment.'), 404); } @@ -105,14 +101,12 @@ class AttachmentAction extends Action */ protected function handle() { - parent::handle(); - if (empty($this->attachment->filename)) { // if it's not a local file, gtfo common_redirect($this->attachment->url, 303); } - $this->showPage(); + parent::handle(); } /** diff --git a/actions/attachment_thumbnail.php b/actions/attachment_thumbnail.php index b5173efa77..b564dee50e 100644 --- a/actions/attachment_thumbnail.php +++ b/actions/attachment_thumbnail.php @@ -27,7 +27,7 @@ * @link http://status.net/ */ -if (!defined('GNUSOCIAL') && !defined('STATUSNET')) { exit(1); } +if (!defined('GNUSOCIAL')) { exit(1); } /** * Show notice attachments @@ -55,11 +55,6 @@ class Attachment_thumbnailAction extends AttachmentAction return true; } - /** - * Show page, a template method. - * - * @return nothing - */ function showPage() { // Returns a File_thumbnail object or throws exception if not available diff --git a/lib/attachment.php b/lib/attachment.php new file mode 100644 index 0000000000..c55b07d7cc --- /dev/null +++ b/lib/attachment.php @@ -0,0 +1,185 @@ +. + * + * @category UI + * @package StatusNet + * @author Evan Prodromou + * @author Sarven Capadisli + * @copyright 2008 StatusNet, Inc. + * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0 + * @link http://status.net/ + */ + +if (!defined('GNUSOCIAL')) { exit(1); } + +/** + * used for one-off attachment action + */ +class Attachment extends AttachmentListItem +{ + function showLink() { + if (Event::handle('StartShowAttachmentLink', array($this->out, $this->attachment))) { + $this->out->elementStart('div', array('id' => 'attachment_view', + 'class' => 'hentry')); + $this->out->elementStart('div', 'entry-title'); + $this->out->element('a', $this->linkAttr(), $this->linkTitle()); + $this->out->elementEnd('div'); + + $this->out->elementStart('div', 'entry-content'); + $this->showRepresentation(); + $this->out->elementEnd('div'); + Event::handle('EndShowAttachmentLink', array($this->out, $this->attachment)); + $this->out->elementEnd('div'); + } + } + + function show() { + $this->showNoticeAttachment(); + } + + function linkAttr() { + return array('rel' => 'external', 'href' => $this->attachment->url); + } + + function linkTitle() { + return $this->attachment->url; + } + + function showRepresentation() { + if (Event::handle('StartShowAttachmentRepresentation', array($this->out, $this->attachment))) { + if (!empty($this->attachment->mimetype)) { + switch ($this->attachment->mimetype) { + case 'image/gif': + case 'image/png': + case 'image/jpg': + case 'image/jpeg': + $this->out->element('img', array('src' => $this->attachment->url, 'alt' => 'alt')); + break; + + case 'application/ogg': + $arr = array('type' => $this->attachment->mimetype, + 'data' => $this->attachment->url, + 'width' => 320, + 'height' => 240 + ); + $this->out->elementStart('object', $arr); + $this->out->element('param', array('name' => 'src', 'value' => $this->attachment->url)); + $this->out->element('param', array('name' => 'autoStart', 'value' => 1)); + $this->out->elementEnd('object'); + break; + + case 'audio/ogg': + case 'audio/x-speex': + case 'video/mpeg': + case 'audio/mpeg': + case 'video/mp4': + case 'video/ogg': + case 'video/quicktime': + case 'video/webm': + $mediatype = common_get_mime_media($this->attachment->mimetype); + try { + $thumb = $this->attachment->getThumbnail(); + $poster = $thumb->getUrl(); + unset ($thumb); + } catch (Exception $e) { + $poster = null; + } + $this->out->elementStart($mediatype, + array('class'=>'attachment_player', + 'poster'=>$poster, + 'controls'=>'controls')); + $this->out->element('source', + array('src'=>$this->attachment->url, + 'type'=>$this->attachment->mimetype)); + $this->out->elementEnd($mediatype); + break; + + case 'text/html': + if ($this->attachment->filename) { + // Locally-uploaded HTML. Scrub and display inline. + $this->showHtmlFile($this->attachment); + break; + } + // Fall through to default. + + default: + Event::handle('ShowUnsupportedAttachmentRepresentation', array($this->out, $this->attachment)); + } + } else { + Event::handle('ShowUnsupportedAttachmentRepresentation', array($this->out, $this->attachment)); + } + } + Event::handle('EndShowAttachmentRepresentation', array($this->out, $this->attachment)); + } + + protected function showHtmlFile(File $attachment) + { + $body = $this->scrubHtmlFile($attachment); + if ($body) { + $this->out->raw($body); + } + } + + /** + * @return mixed false on failure, HTML fragment string on success + */ + protected function scrubHtmlFile(File $attachment) + { + $path = File::path($attachment->filename); + if (!file_exists($path) || !is_readable($path)) { + common_log(LOG_ERR, "Missing local HTML attachment $path"); + return false; + } + $raw = file_get_contents($path); + + // Normalize... + $dom = new DOMDocument(); + if(!$dom->loadHTML($raw)) { + common_log(LOG_ERR, "Bad HTML in local HTML attachment $path"); + return false; + } + + // Remove