X-Git-Url: https://git.cyclocoop.org/%28%28?a=blobdiff_plain;f=includes%2Fcontent%2FJsonContent.php;h=1d9ee33804bf2a235f38922b50675719c0349400;hb=a6c17640fc571ebd173e5460bfbda599cf5f5f67;hp=ff3b25b8b262079528219b551f5cfbf93ec9b32e;hpb=13d083b2065092b4bc48288a8ecdee9270fdb19e;p=lhc%2Fweb%2Fwiklou.git diff --git a/includes/content/JsonContent.php b/includes/content/JsonContent.php index ff3b25b8b2..1d9ee33804 100644 --- a/includes/content/JsonContent.php +++ b/includes/content/JsonContent.php @@ -2,8 +2,6 @@ /** * JSON Content Model * - * This class requires the root structure to be an object (not primitives or arrays). - * * @file * * @author Ori Livneh @@ -25,8 +23,8 @@ class JsonContent extends TextContent { /** * @param string $text JSON */ - public function __construct( $text ) { - parent::__construct( $text, CONTENT_MODEL_JSON ); + public function __construct( $text, $modelId = CONTENT_MODEL_JSON ) { + parent::__construct( $text, $modelId ); } /** @@ -41,7 +39,10 @@ class JsonContent extends TextContent { } /** - * Decodes the JSON string into a PHP object. + * Decodes the JSON string. + * + * Note that this parses it without casting objects to associative arrays. + * Objects and arrays are kept as distinguishable types in the PHP values. * * @return Status */ @@ -56,7 +57,7 @@ class JsonContent extends TextContent { * @return bool Whether content is valid. */ public function isValid() { - return $this->getData()->isGood() && is_object( $this->getData()->getValue() ); + return $this->getData()->isGood(); } /** @@ -103,7 +104,7 @@ class JsonContent extends TextContent { // FIXME: WikiPage::doEditContent generates parser output before validation. // As such, native data may be invalid (though output is discarded later in that case). if ( $generateHtml && $this->isValid() ) { - $output->setText( $this->objectTable( $this->getData()->getValue() ) ); + $output->setText( $this->rootValueTable( $this->getData()->getValue() ) ); $output->addModuleStyles( 'mediawiki.content.json' ); } else { $output->setText( '' ); @@ -111,9 +112,35 @@ class JsonContent extends TextContent { } /** - * Construct an HTML representation of a JSON object. + * Construct HTML table representation of any JSON value. * - * Called recursively via valueCell(). + * See also valueCell, which is similar. + * + * @param mixed $val + * @return string HTML. + */ + protected function rootValueTable( $val ) { + if ( is_object( $val ) ) { + return self::objectTable( $val ); + } + + if ( is_array( $val ) ) { + // Wrap arrays in another array so that they're visually boxed in a container. + // Otherwise they are visually indistinguishable from a single value. + return self::arrayTable( array( $val ) ); + } + + return Html::rawElement( 'table', array( 'class' => 'mw-json mw-json-single-value' ), + Html::rawElement( 'tbody', array(), + Html::rawElement( 'tr', array(), + Html::element( 'td', array(), self::primitiveValue( $val ) ) + ) + ) + ); + } + + /** + * Create HTML table representing a JSON object. * * @param stdClass $mapping * @return string HTML @@ -134,26 +161,25 @@ class JsonContent extends TextContent { ); } return Html::rawElement( 'table', array( 'class' => 'mw-json' ), - Html::rawElement( 'tbody', array(), join( "\n", $rows ) ) + Html::rawElement( 'tbody', array(), join( '', $rows ) ) ); } /** - * Construct HTML representation of a single key-value pair. + * Create HTML table row representing one object property. + * * @param string $key * @param mixed $val * @return string HTML. */ protected function objectRow( $key, $val ) { - $th = Xml::elementClean( 'th', array(), $key ); + $th = Html::element( 'th', array(), $key ); $td = self::valueCell( $val ); return Html::rawElement( 'tr', array(), $th . $td ); } /** - * Constructs an HTML representation of a JSON array. - * - * Called recursively via valueCell(). + * Create HTML table representing a JSON array. * * @param array $mapping * @return string HTML @@ -179,7 +205,8 @@ class JsonContent extends TextContent { } /** - * Construct HTML representation of a single array value. + * Create HTML table row representing the value in an array. + * * @param mixed $val * @return string HTML. */ @@ -189,7 +216,8 @@ class JsonContent extends TextContent { } /** - * Construct HTML representation of a single value. + * Construct HTML table cell representing any JSON value. + * * @param mixed $val * @return string HTML. */ @@ -197,15 +225,26 @@ class JsonContent extends TextContent { if ( is_object( $val ) ) { return Html::rawElement( 'td', array(), self::objectTable( $val ) ); } + if ( is_array( $val ) ) { return Html::rawElement( 'td', array(), self::arrayTable( $val ) ); } + + return Html::element( 'td', array( 'class' => 'value' ), self::primitiveValue( $val ) ); + } + + /** + * Construct text representing a JSON primitive value. + * + * @param mixed $val + * @return string Text. + */ + protected function primitiveValue( $val ) { if ( is_string( $val ) ) { - $val = '"' . $val . '"'; - } else { - $val = FormatJson::encode( $val ); + // Don't FormatJson::encode for strings since we want quotes + // and new lines to render visually instead of escaped. + return '"' . $val . '"'; } - - return Xml::elementClean( 'td', array( 'class' => 'value' ), $val ); + return FormatJson::encode( $val ); } }