/** * @dataProvider escapeHtmlProvider() */ public function testEscapeHtml($text, $full_encode, $double_encode, $expected) { $this->assertSame($expected, String::escapeHTML($text, $full_encode, $double_encode), 'Escaping using function'); if (!$double_encode) { // we can't force double-encoding off for the generic escape() method // as it's usually the sensible behaviour. return; } $ctx = RenderContext::create(RenderContext::TYPE_HTML4_STRICT); RenderContext::push($ctx); $this->assertSame($expected, String::escape($text, null, $full_encode), 'Escaping using HTML RenderContext'); $ctx = RenderContext::create(RenderContext::TYPE_XHTML1_STRICT); RenderContext::push($ctx); $this->assertSame($expected, String::escape($text, null, $full_encode), 'Escaping using XHTML RenderContext'); RenderContext::pop(); RenderContext::pop(); $this->assertSame($expected, String::escape($text, RenderContext::CONTENT_HTML, $full_encode), 'Escaping using HTML content override'); $this->assertSame($expected, String::escape($text, RenderContext::CONTENT_XHTML, $full_encode), 'Escaping using XHTML content override'); }
/** * Performs a simple redirection to the specified URL (see below for details * on shorthand URLs). * * Shorthand URLs work as follows: * - <kbd>/^#/</kbd> -- Appends a URL hash to the current URL. * - <kbd>/^?/</kbd> -- Sets the query string for the current page. * - <kbd>/^&/</kbd> -- Appends all specified queries to the URL (Overwrite). * - <kbd>/^&&/</kbd> -- Appends all specified queries to the URL (No overwrite). * - <kbd>/^\//</kbd> -- Redirects to URL relative to root of site (prepends domain). * - <kbd>/^[a-z]*:\/\//</kbd> -- Redirects to absolute URL. * * There is also support for pausing redirects for debugging purposes. * * @see Debug::pauseOnRedirect() * * @param string $url Where to redirect to. * @param bool $permanent Whether to redirect permanently (default: false) * * @throws RedirectorException */ public static function redirect($url = null, $permanent = false) { $url = URL::ize($url); # Get the current render context $ctx = RenderContext::get(); # Check whether we should suspend redirects if (Debug::isEnabled() && (Debug::pauseOnRedirect() || Error::hasErred())) { echo '<div>'; printf('<p><strong>Paused Redirect:</strong> <a href="%s">%s</a></p>', $url, String::escapeHTML($url)); if (Error::hasErred()) { echo '<p><strong>Last Error:</strong></p>'; Debug::out(Error::getLast()); } echo '</div>'; exit; } # Write and close session to avoid losing changes: session_write_close(); # Perform redirect if (headers_sent()) { switch ($ctx->getLanguage()) { case RenderContext::LANG_HTML: case RenderContext::LANG_XHTML: $url = String::escapeJS($url, false); echo '<script type="text/javascript">window.location = \'' . $url . '\';</script>"'; break; default: throw new RedirectorException('Cannot redirect - headers sent and invalid render context.'); } } else { if ($permanent) { header('HTTP/1.1 301 Moved Permanently'); } header('Location: ' . $url); } # Output message just in case we have a silly browser [RFC2616] if (isset($_SERVER['REQUEST_METHOD']) && $_SERVER['REQUEST_METHOD'] != 'HEAD') { switch ($ctx->getLanguage()) { case RenderContext::LANG_HTML: case RenderContext::LANG_XHTML: printf('Redirecting to: <a href="%s">%s</a>.', $url, String::escapeHTML($url)); break; default: # Ignore } } # We've redirected, so stop executing now exit; }
/** * Generate a list of records in the given table. * * If the given table is null, then all tables defined in the schema will be * listed. * * @param string $table The table from which records should be listed. * * @return string */ public function generateListPage($table) { ob_start(); if (is_null($table)) { // list all tables $this->outputPageHeader('All tables'); # $_GET[self::FORM_PREFIX.'_table'] echo "<ul>\n"; foreach (array_keys($this->schema) as $table) { echo '<li><a href="' . $this->generateActionUrl('list') . '&' . self::FORM_PREFIX . '_table=' . rawurlencode($table) . '">' . String::escape($table) . "</a></li>\n"; } echo "</ul>\n"; } else { // specific table $this->outputPageHeader('Table ' . $table); $db = $this->db; $primary_field = $this->schema[$table]['_primary']; // join with belongsTo tables (and hasMany?) if (count($this->schema[$table]['_belongsTo'])) { $sql = 'SELECT * FROM `' . $table . '` ORDER BY `' . $primary_field . '`'; $select = array(); $from = array(''); # critical hack to include one LEFT JOIN foreach (array_keys($this->schema[$table]['fields']) as $field) { if (isset($this->schema[$table]['_belongsTo'][$field])) { $linked_table = $this->schema[$table]['_belongsTo'][$field]; if (isset($this->schema[$linked_table]['_primary'])) { $linked_field = $this->schema[$linked_table]['_primary']; $linked_display_field = $this->schema[$linked_table]['_primary']; if (isset($this->schema[$linked_table]['_display'])) { $linked_display_field = $this->schema[$linked_table]['_display']; } $select[] = 'CONCAT(`' . $linked_table . '`.`' . $linked_display_field . '`, \' [\', `' . $table . '`.`' . $field . '`, \']\') AS `' . $field . '`'; $from[] = '`' . $linked_table . '` ON `' . $linked_table . '`.`' . $linked_field . '` = `' . $table . '`.`' . $field . '`'; } else { $select[] = '`' . $table . '`.`' . $field . '`'; } } else { $select[] = '`' . $table . '`.`' . $field . '`'; } } $sql = 'SELECT ' . implode(', ', $select) . ' FROM `' . $table . '`' . implode(' LEFT JOIN ', $from) . ' ORDER BY `' . $table . '`.`' . $primary_field . '`'; } else { $sql = 'SELECT * FROM `' . $table . '` ORDER BY `' . $primary_field . '`'; } $stmt = $db->prepare($sql); $stmt->execute(); if ($stmt->rowCount()) { $header = false; echo "<table class=\"scaffold\">\n<thead>\n<tr>"; $row = $stmt->fetch(\PDO::FETCH_ASSOC); foreach (array_keys($row) as $col) { echo '<th>' . String::escapeHTML($col) . '</th>'; } echo '<th class="actions">Actions</th>'; echo "</tr>\n</thead>\n<tfoot></tfoot>\n<tbody>\n"; $i = 0; do { echo '<tr class="zebra' . $i++ % 2 . '">'; foreach ($row as $k => $v) { if ($k === $primary_field) { echo '<td class="primary">' . String::escapeHTML($v) . '</td>'; } else { echo '<td>' . String::escapeHTML($v) . '</td>'; } } echo '<td class="actions"><a href="' . $this->generateActionUrl('update', $row[$primary_field]) . '">Edit</a> <a href="' . $this->generateActionUrl('delete', $row[$primary_field]) . '">Delete</a></th>'; echo "</tr>\n"; } while ($row = $stmt->fetch(\PDO::FETCH_ASSOC)); echo "</tbody>\n</table>\n"; } else { echo '<p>No rows to display.</p>', "\n"; } echo '<p><a href="' . $this->generateActionUrl('create') . '">New item</a></p>', "\n"; } $this->outputPageFooter(); return ob_get_clean(); }