/** * Create a property, either from server data or locally * * To indicate a property has newly been created locally, make sure to pass * true for the $new parameter. * * @param object $factory an object factory implementing "get" as described in \jackalope\Factory * @param array $data array with fields * type (integer or string from PropertyType) * and value (data for creating value object - array for multivalue property) * @param string $path the absolute path of this item * @param Session the session instance * @param ObjectManager the objectmanager instance - the caller has to take care of registering this item with the object manager * @param boolean $new optional: set to true to make this property aware its not yet existing on the server. defaults to false */ public function __construct($factory, array $data, $path, Session $session, ObjectManager $objectManager, $new = false) { parent::__construct($factory, $path, $session, $objectManager, $new); $type = $data['type']; if (is_string($type)) { $type = \PHPCR\PropertyType::valueFromName($type); } elseif (!is_numeric($type)) { throw new \PHPCR\RepositoryException("INTERNAL ERROR -- No valid type specified ({$type})"); } else { //sanity check. this will throw InvalidArgumentException if $type is not a valid type \PHPCR\PropertyType::nameFromValue($type); } $this->type = $type; if (is_array($data['value'])) { $this->isMultiple = true; $this->value = array(); foreach ($data['value'] as $value) { $this->value[] = Helper::convertType($value, $type); } } elseif (null !== $data['value']) { $this->value = Helper::convertType($data['value'], $type); } else { throw new \PHPCR\RepositoryException('INTERNAL ERROR -- data[value] may not be null'); } }
/** * {@inheritDoc} */ public function normalize($node, $format = null, array $context = array()) { $res = array(); foreach ($node->getProperties() as $property) { if (false === $this->isPropertyEditable($property)) { continue; } $propertyType = $property->getType(); $propertyValue = $property->getValue(); $propertyName = $property->getName(); if (in_array($property->getType(), array(PropertyType::REFERENCE, PropertyType::WEAKREFERENCE))) { $nodeUuids = array(); if (false === is_array($propertyValue)) { $propertyValue = array($propertyValue); } foreach ($propertyValue as $node) { $nodeUuids[] = $node->getIdentifier(); } $propertyValue = $nodeUuids; if (false === $property->isMultiple()) { $propertyValue = reset($propertyValue); } } $res[$propertyName] = array('type' => PropertyType::nameFromValue($propertyType), 'value' => $propertyValue); } return $res; }
public function setProperty($name, $value = null, $type = 'String') { if (is_integer($type)) { $type = PropertyType::nameFromValue($type); } $this->properties[$name] = array('value' => $value, 'type' => $type); }
/** * Convert a node type into YAML format * * @param NodeTypeInterface * * @return string */ public function serialize(NodeTypeInterface $nt) { $out = array('name' => $nt->getName(), 'declared_supertypes' => $nt->getDeclaredSupertypeNames(), 'abstract' => (bool) $nt->isAbstract(), 'mixin' => (bool) $nt->isMixin(), 'orderable_child_nodes' => (bool) $nt->hasOrderableChildNodes(), 'queryable' => (bool) $nt->isQueryable(), 'primary_item' => $nt->getPrimaryItemName(), 'properties' => array(), 'children' => array()); foreach ($nt->getDeclaredPropertyDefinitions() as $pd) { $property = $this->getItemDefinitionArray($pd); $property = array_merge($property, array('required_type' => PropertyType::nameFromValue($pd->getRequiredType()), 'value_constraints' => $pd->getValueConstraints(), 'default_values' => $pd->getDefaultValues(), 'multiple' => (bool) $pd->isMultiple(), 'available_query_operators' => $pd->getAvailableQueryOperators(), 'full_text_searchable' => (bool) $pd->isFullTextSearchable(), 'query_orderable' => (bool) $pd->isQueryOrderable())); $out['properties'][] = $property; } foreach ($nt->getDeclaredChildNodeDefinitions() as $cd) { $child = $this->getItemDefinitionArray($cd); $child = array_merge($child, array('required_primary_types' => $cd->getRequiredPrimaryTypeNames(), 'default_primary_type' => $cd->getDefaultPrimaryTypeName(), 'same_name_siblings' => (bool) $cd->allowsSameNameSiblings())); $out['children'][] = $child; } return Yaml::dump($out, 10); }
private function renderProperties($currentNode, $table, $spacers, $filter = null) { $properties = (array) $currentNode->getProperties($filter ?: null); $properties = $this->sort($properties); try { $primaryItem = $currentNode->getPrimaryItem(); } catch (ItemNotFoundException $e) { $primaryItem = null; } $nodeType = $currentNode->getPrimaryNodeType(); $propertyDefinitions = $nodeType->getDeclaredPropertyDefinitions(); $propertyNames = array(); foreach ($propertyDefinitions as $name => $propertyDefinition) { $propertyNames[$propertyDefinition->getName()] = $propertyDefinition; } $i = 0; foreach ($properties as $name => $property) { try { $i++; if (isset($propertyNames[$name])) { unset($propertyNames[$name]); } $valueCell = $this->formatter->formatValue($property); } catch (\Exception $e) { $valueCell = '<error>' . $e->getMessage() . '</error>'; } $table->addRow(array('<property>' . implode('', $spacers) . $name . '</property>', sprintf('<property-type>%s (%s)</property-type>', $this->formatter->getPropertyTypeName($property->getType()), implode(',', (array) $property->getLength()) ?: '0'), $valueCell)); } if ($this->showTemplate) { foreach ($propertyNames as $propertyName => $property) { $table->addRow(array('<templateproperty>' . implode('', $spacers) . '@' . $propertyName . '</templateproperty>', '<property-type>' . strtoupper(PropertyType::nameFromValue($property->getRequiredType())) . '</property-type>', '')); } } }
/** * Seperate properties array into an xml and binary data. * * @param array $properties * * @return array ( * 'stringDom' => $stringDom, * 'numericalDom' => $numericalDom', * 'binaryData' => streams, * 'references' => array('type' => INT, 'values' => array(UUIDs))) */ private function propsToXML($properties) { $namespaces = array('mix' => "http://www.jcp.org/jcr/mix/1.0", 'nt' => "http://www.jcp.org/jcr/nt/1.0", 'xs' => "http://www.w3.org/2001/XMLSchema", 'jcr' => "http://www.jcp.org/jcr/1.0", 'sv' => "http://www.jcp.org/jcr/sv/1.0", 'rep' => "internal"); $doms = array('stringDom' => array(), 'numericalDom' => array()); $binaryData = $references = array(); foreach ($properties as $property) { $targetDoms = array('stringDom'); switch ($property->getType()) { case PropertyType::WEAKREFERENCE: case PropertyType::REFERENCE: $references[$property->getName()] = array('type' => $property->getType(), 'values' => $property->isMultiple() ? $property->getString() : array($property->getString())); case PropertyType::NAME: case PropertyType::URI: case PropertyType::PATH: case PropertyType::STRING: $values = $property->getString(); break; case PropertyType::DECIMAL: $values = $property->getDecimal(); $targetDoms[] = 'numericalDom'; break; case PropertyType::BOOLEAN: $values = array_map('intval', (array) $property->getBoolean()); break; case PropertyType::LONG: $values = $property->getLong(); $targetDoms[] = 'numericalDom'; break; case PropertyType::BINARY: if ($property->isNew() || $property->isModified()) { $values = array(); foreach ((array) $property->getValueForStorage() as $stream) { if (null === $stream) { $binary = ''; } else { $binary = stream_get_contents($stream); fclose($stream); } $binaryData[$property->getName()][] = $binary; $length = strlen($binary); $values[] = $length; } } else { $values = $property->getLength(); if (!$property->isMultiple() && empty($values)) { $values = array(0); } } break; case PropertyType::DATE: $values = $property->getDate(); if ($values instanceof \DateTime) { $values = array($values); } foreach ((array) $values as $key => $date) { if ($date instanceof \DateTime) { // do not modify the instance which is associated with the node. $date = clone $date; // normalize to UTC for storage. $date->setTimezone(new \DateTimeZone('UTC')); } $values[$key] = $date; } $values = $this->valueConverter->convertType($values, PropertyType::STRING); break; case PropertyType::DOUBLE: $values = $property->getDouble(); $targetDoms[] = 'numericalDom'; break; default: throw new RepositoryException('unknown type ' . $property->getType()); } foreach ($targetDoms as $targetDom) { $doms[$targetDom][] = array('name' => $property->getName(), 'type' => PropertyType::nameFromValue($property->getType()), 'multiple' => $property->isMultiple(), 'lengths' => (array) $property->getLength(), 'values' => $values); } } $ret = array('stringDom' => null, 'numericalDom' => null, 'binaryData' => $binaryData, 'references' => $references); foreach ($doms as $targetDom => $properties) { $dom = new \DOMDocument('1.0', 'UTF-8'); $rootNode = $dom->createElement('sv:node'); foreach ($namespaces as $namespace => $uri) { $rootNode->setAttribute('xmlns:' . $namespace, $uri); } $dom->appendChild($rootNode); foreach ($properties as $property) { /* @var $property Property */ $propertyNode = $dom->createElement('sv:property'); $propertyNode->setAttribute('sv:name', $property['name']); $propertyNode->setAttribute('sv:type', $property['type']); $propertyNode->setAttribute('sv:multi-valued', $property['multiple'] ? '1' : '0'); $lengths = (array) $property['lengths']; foreach ((array) $property['values'] as $key => $value) { $element = $propertyNode->appendChild($dom->createElement('sv:value')); $element->appendChild($dom->createTextNode($value)); if (isset($lengths[$key])) { $lengthAttribute = $dom->createAttribute('length'); $lengthAttribute->value = $lengths[$key]; $element->appendChild($lengthAttribute); } } $rootNode->appendChild($propertyNode); } if (count($properties)) { $ret[$targetDom] = $dom; } } return $ret; }
/** * Create a property, either from server data or locally * * To indicate a property has newly been created locally, make sure to pass * true for the $new parameter. In that case, you should pass an empty array * for $data and use setValue afterwards to let the type magic be handled. * Then multivalue is determined on setValue * * For binary properties, the value is the length of the data(s), not the * data itself. * * @param FactoryInterface $factory the object factory * @param array $data array with fields <tt>type</tt> (integer or string * from PropertyType) and <tt>value</tt> (data for creating the * property value - array for multivalue property) * @param string $path the absolute path of this item * @param Session $session the session instance * @param ObjectManager $objectManager the objectManager instance - the caller has to take * care of registering this item with the object manager * @param boolean $new optional: set to true to make this property aware * its not yet existing on the server. defaults to false */ public function __construct(FactoryInterface $factory, array $data, $path, Session $session, ObjectManager $objectManager, $new = false) { parent::__construct($factory, $path, $session, $objectManager, $new); $this->wrapBinaryStreams = $session->getRepository()->getDescriptor(Repository::JACKALOPE_OPTION_STREAM_WRAPPER); if (empty($data) && $new) { return; } if (!isset($data['value'])) { throw new InvalidArgumentException("Can't create property at {$path} without any data"); } if (isset($data['type']) && PropertyType::UNDEFINED !== $data['type']) { $type = $data['type']; if (is_string($type)) { $type = PropertyType::valueFromName($type); } elseif (!is_numeric($type)) { // @codeCoverageIgnoreStart throw new RepositoryException("INTERNAL ERROR -- No valid type specified ({$type})"); // @codeCoverageIgnoreEnd } else { //sanity check. this will throw InvalidArgumentException if $type is not a valid type PropertyType::nameFromValue($type); } } else { // we are creating a node $type = PropertyType::determineType(is_array($data['value']) ? reset($data['value']) : $data['value']); } $this->type = $type; if ($type == PropertyType::BINARY && !$new) { // reading a binary property from backend, we do not get the stream immediately but just the size if (is_array($data['value'])) { $this->isMultiple = true; } $this->length = $data['value']; $this->value = null; return; } if (is_array($data['value'])) { $this->isMultiple = true; $this->value = array(); foreach ($data['value'] as $value) { $this->value[] = PropertyType::convertType($value, $type); } } elseif (null !== $data['value']) { $this->value = PropertyType::convertType($data['value'], $type); } else { // @codeCoverageIgnoreStart throw new RepositoryException('INTERNAL ERROR -- data[value] may not be null'); // @codeCoverageIgnoreEnd } }
/** * "Decode" PHPCR property to MongoDB property * * @param $property * @return array|null * * @throws \Exception */ private function decodeProperty(PropertyInterface $property) { $path = $property->getPath(); $path = $this->validatePath($path); $name = explode('/', $path); $name = end($name); if ($name == 'jcr:uuid' || $name == 'jcr:primaryType') { return null; } if (!$property->isModified() && !$property->isNew()) { return null; } $propType = $property->getType(); $propNode = $property->getNode(); if (($propType == PropertyType::REFERENCE || $propType == PropertyType::WEAKREFERENCE) && ($propNode instanceof NodeInterface && !$propNode->isNodeType('mix:referenceable'))) { throw new ValueFormatException('Node ' . $property->getNode()->getPath() . ' is not referenceable.'); } $isMultiple = $property->isMultiple(); $typeId = $property->getType(); $type = PropertyType::nameFromValue($typeId); $data = array('multi' => $isMultiple, 'name' => $property->getName(), 'type' => $type); $binaryData = null; switch ($typeId) { case PropertyType::NAME: case PropertyType::URI: case PropertyType::WEAKREFERENCE: case PropertyType::REFERENCE: case PropertyType::PATH: $values = $property->getString(); break; case PropertyType::DECIMAL: $values = $property->getDecimal(); break; case PropertyType::STRING: $values = $property->getString(); break; case PropertyType::BOOLEAN: $values = $property->getBoolean(); break; case PropertyType::LONG: $values = $property->getLong(); break; case PropertyType::BINARY: if ($property->isMultiple()) { foreach ((array) $property->getBinary() as $binary) { $binary = stream_get_contents($binary); $binaryData[] = $binary; $values[] = strlen($binary); } } else { $binary = stream_get_contents($property->getBinary()); $binaryData[] = $binary; $values = strlen($binary); } break; case PropertyType::DATE: if ($property->isMultiple()) { $dates = $property->getDate() ?: new \DateTime('now'); foreach ((array) $dates as $date) { $value = array('date' => new \MongoDate($date->getTimestamp()), 'timezone' => $date->getTimezone()->getName()); $values[] = $value; } } else { $date = $property->getDate() ?: new \DateTime('now'); $values = array('date' => new \MongoDate($date->getTimestamp()), 'timezone' => $date->getTimezone()->getName()); } break; case PropertyType::DOUBLE: $values = $property->getDouble(); break; } if ($isMultiple) { $data['value'] = array(); foreach ((array) $values as $value) { $this->assertValidPropertyValue($data['type'], $value, $path); $data['value'][] = $value; } } else { $this->assertValidPropertyValue($data['type'], $values, $path); $data['value'] = $values; } if ($binaryData) { try { foreach ($binaryData as $idx => $binary) { $grid = $this->db->getGridFS(); $grid->getMongoCollection()->storeBytes($binary, array('path' => $path, 'w_id' => $this->workspaceId, 'idx' => $idx)); } } catch (\Exception $e) { throw $e; } } return $data; }
/** * Internally used to set the value of the property without any notification * of changes nor state change. * * @param mixed $value The value to set. * @param int|string $type PropertyType constant * @param boolean $constructor Whether this is called from the constructor. * * @see Property::setValue() * * @throws AccessDeniedException * @throws ItemNotFoundException * @throws LockException * @throws ConstraintViolationException * @throws RepositoryException * @throws VersionException * @throws InvalidArgumentException * @throws ValueFormatException * * @private */ public function _setValue($value, $type = PropertyType::UNDEFINED, $constructor = false) { if (null === $value) { $this->remove(); return; } if (is_string($type)) { $type = PropertyType::valueFromName($type); } elseif (!is_numeric($type)) { // @codeCoverageIgnoreStart throw new RepositoryException("INTERNAL ERROR -- No valid type specified ({$type})"); // @codeCoverageIgnoreEnd } else { //sanity check. this will throw InvalidArgumentException if $type is not a valid type PropertyType::nameFromValue($type); } if ($constructor || $this->isNew()) { $this->isMultiple = is_array($value); } if (is_array($value) && !$this->isMultiple) { throw new ValueFormatException('Can not set a single value property (' . $this->name . ') with an array of values'); } if ($this->isMultiple && is_scalar($value)) { throw new ValueFormatException('Can not set a multivalue property (' . $this->name . ') with a scalar value'); } if ($this->isMultiple) { foreach ($value as $key => $v) { if (null === $v) { unset($value[$key]); } } } //TODO: check if changing type allowed. /* * if ($type !== null && ! canHaveType($type)) { * throw new ConstraintViolationException("Can not set this property to type ".PropertyType::nameFromValue($type)); * } */ if (PropertyType::UNDEFINED === $type) { // avoid changing type of multivalue property with empty array if (!$this->isMultiple() || count($value) || PropertyType::UNDEFINED === $this->type) { $type = $this->valueConverter->determineType($value); } else { $type = $this->type; } } $targetType = $type; /* * TODO: find out with node type definition if the new type is allowed if ($this->type !== $type) { if (!canHaveType($type)) { //convert to an allowed type } } */ if (PropertyType::BINARY !== $targetType || $constructor && $this->isNew() || !$this->isNew() && PropertyType::UNDEFINED !== $this->type && $this->type !== $targetType) { $value = $this->valueConverter->convertType($value, $targetType, $constructor ? PropertyType::UNDEFINED : $type); } if (PropertyType::BINARY === $targetType) { if ($constructor && !$this->isNew()) { // reading a binary property from backend, we do not get the stream immediately but just the size if (is_array($value)) { $this->isMultiple = true; } $this->type = PropertyType::BINARY; $this->length = $value; $this->value = null; return; } if (is_array($value)) { $this->length = array(); foreach ($value as $v) { $stat = is_resource($v) ? fstat($v) : array('size' => -1); $this->length[] = $stat['size']; } } elseif (is_resource($value)) { $stat = fstat($value); $this->length = $stat['size']; } else { $this->length = -1; } } $this->type = $targetType; $this->value = $value; }
/** * Recursively output node and all its children into the file in the system * view format * * @param NodeInterface $node the node to output * @param resource $stream The stream resource (i.e. acquired with fopen) to * which the XML serialization of the subgraph will be output. Must * support the fwrite method. * @param boolean $skipBinary A boolean governing whether binary properties * are to be serialized. * @param boolean $noRecurse A boolean governing whether the subgraph at * absPath is to be recursed. * @param boolean $root Whether this is the root node of the resulting * document, meaning the namespace declarations have to be included in * it. */ private static function exportSystemViewRecursive(NodeInterface $node, NamespaceRegistryInterface $ns, $stream, $skipBinary, $noRecurse, $root = false) { fwrite($stream, '<sv:node'); if ($root) { self::exportNamespaceDeclarations($ns, $stream); } fwrite($stream, ' sv:name="' . (0 === $node->getDepth() ? 'jcr:root' : htmlspecialchars($node->getName())) . '">'); // the order MUST be primary type, then mixins, if any, then jcr:uuid if its a referenceable node fwrite($stream, '<sv:property sv:name="jcr:primaryType" sv:type="Name"><sv:value>' . htmlspecialchars($node->getPropertyValue('jcr:primaryType')) . '</sv:value></sv:property>'); if ($node->hasProperty('jcr:mixinTypes')) { fwrite($stream, '<sv:property sv:name="jcr:mixinTypes" sv:type="Name" sv:multiple="true">'); foreach ($node->getPropertyValue('jcr:mixinTypes') as $type) { fwrite($stream, '<sv:value>' . htmlspecialchars($type) . '</sv:value>'); } fwrite($stream, '</sv:property>'); } if ($node->isNodeType('mix:referenceable')) { fwrite($stream, '<sv:property sv:name="jcr:uuid" sv:type="String"><sv:value>' . $node->getIdentifier() . '</sv:value></sv:property>'); } foreach ($node->getProperties() as $name => $property) { /** @var $property \PHPCR\PropertyInterface */ if ($name == 'jcr:primaryType' || $name == 'jcr:mixinTypes' || $name == 'jcr:uuid') { // explicitly handled before continue; } if (PropertyType::BINARY == $property->getType() && $skipBinary) { // do not output binary data in the xml continue; } fwrite($stream, '<sv:property sv:name="' . htmlentities($name) . '" sv:type="' . PropertyType::nameFromValue($property->getType()) . '"' . ($property->isMultiple() ? ' sv:multiple="true"' : '') . '>'); $values = $property->isMultiple() ? $property->getString() : array($property->getString()); foreach ($values as $value) { if (PropertyType::BINARY == $property->getType()) { $val = base64_encode($value); } else { $val = htmlspecialchars($value); //TODO: can we still have invalid characters after this? if so base64 and property, xsi:type="xsd:base64Binary" } fwrite($stream, "<sv:value>{$val}</sv:value>"); } fwrite($stream, "</sv:property>"); } if (!$noRecurse) { foreach ($node as $child) { if (!($child->getDepth() == 1 && NodeHelper::isSystemItem($child))) { self::exportSystemViewRecursive($child, $ns, $stream, $skipBinary, $noRecurse); } } } fwrite($stream, '</sv:node>'); }
/** * @Given /^the property "([^"]*)" should have type "([^"]*)" and value "([^"]*)"$/ */ public function thePropertyShouldHaveTypeAndValue($arg1, $arg2, $arg3) { $session = $this->getSession(); $property = $session->getItem($arg1); if (!$property instanceof PropertyInterface) { throw new \InvalidArgumentException(sprintf('Item at "%s" is not a property', $arg1)); } \PHPUnit_Framework_Assert::assertEquals($arg2, PropertyType::nameFromValue($property->getType())); \PHPUnit_Framework_Assert::assertEquals($arg3, $property->getValue()); }
/** * @expectedException \InvalidArgumentException */ public function testNameFromValueInvalid() { PropertyType::nameFromValue(-1); }
protected function getMimePart($name, $value, $mime_boundary) { $data = ''; $eol = "\r\n"; if (is_array($value)) { if (is_array($value[0])) { foreach ($value[0] as $v) { $data .= $this->getMimePart($name, array($v, $value[1]), $mime_boundary); } return $data; } $data .= '--' . $mime_boundary . $eol; if (is_resource($value[0])) { $data .= 'Content-Disposition: form-data; name="' . $name . '"; filename="' . $name . '"' . $eol; $data .= 'Content-Type: jcr-value/' . strtolower(PropertyType::nameFromValue($value[1])) . '; charset=UTF-8' . $eol; $data .= 'Content-Transfer-Encoding: binary' . $eol . $eol; $data .= stream_get_contents($value[0]) . $eol; fclose($value[0]); } else { $data .= 'Content-Disposition: form-data; name="' . $name . '"' . $eol; $data .= 'Content-Type: jcr-value/' . strtolower(PropertyType::nameFromValue($value[1])) . '; charset=UTF-8' . $eol; $data .= 'Content-Transfer-Encoding: 8bit' . $eol . $eol; switch ($value[1]) { case PropertyType::DATE: $data .= $this->valueConverter->convertType($value[0], PropertyType::STRING); break; default: $data .= $value[0]; } $data .= $eol; } } else { if (is_array($value)) { foreach ($value as $v) { $data .= $this->getMimePart($name, $v, $mime_boundary); } return $data; } $data .= '--' . $mime_boundary . $eol; $data .= 'Content-Disposition: form-data; name="' . $name . '"' . $eol; $data .= 'Content-Type: text/plain; charset=UTF-8' . $eol; $data .= 'Content-Transfer-Encoding: 8bit' . $eol . $eol; //$data .= '--' . $mime_boundary . $eol; $data .= $value . $eol; } return $data; }
private function writeProperties($properties) { if (null === $properties) { // getDeclaredPropertyDefinitions is allowed to return null on // newly created node type definitions return ''; } $s = ''; /** @var $property PropertyDefinitionInterface */ foreach ($properties as $property) { $this->checkNamespace($property->getName()); $s .= '- ' . $property->getName(); if ($property->getRequiredType()) { $s .= ' (' . PropertyType::nameFromValue($property->getRequiredType()) . ')'; } $s .= "\n"; if ($property->getDefaultValues()) { $s .= "= '" . implode("', '", $property->getDefaultValues()) . "'\n"; } $attributes = ''; if ($property->isMandatory()) { $attributes .= 'mandatory '; } if ($property->isAutoCreated()) { $attributes .= 'autocreated '; } if ($property->isProtected()) { $attributes .= 'protected '; } if ($property->isMultiple()) { $attributes .= 'multiple '; } if ($property->getAvailableQueryOperators()) { $attributes .= implode("', '", $property->getAvailableQueryOperators()); } if (!$property->isFullTextSearchable()) { $attributes .= 'nofulltext '; } if (!$property->isQueryOrderable()) { $attributes .= 'noqueryorder '; } if (OnParentVersionAction::COPY !== $property->getOnParentVersion()) { $attributes .= OnParentVersionAction::nameFromValue($property->getOnParentVersion()) . ' '; } if ($attributes) { $s .= trim($attributes) . "\n"; } if ($property->getValueConstraints()) { $s .= "< '" . implode("', '", $property->getValueConstraints()) . "'\n"; } } return $s; }
/** * Stores a property to the given absolute path * * @param string $path Absolute path to identify a specific property. * @param \PHPCR\PropertyInterface * @return bool true on success * * @throws \PHPCR\RepositoryException if not logged in */ public function storeProperty($path, \PHPCR\PropertyInterface $property) { $this->ensureAbsolutePath($path); $type = \PHPCR\PropertyType::nameFromValue($property->getType()); $request = $this->getRequest(Request::PUT, $path); $nativeValue = $property->getNativeValue(); if ($property->getName() === 'jcr:mixinTypes') { $uri = $this->normalizeUri(dirname($path) === '\\' ? '/' : dirname($path)); $request->setUri($uri); $request->setMethod(Request::PROPPATCH); $body = '<?xml version="1.0" encoding="UTF-8"?>' . '<D:propertyupdate xmlns:D="DAV:">' . '<D:set>' . '<D:prop>' . '<dcr:mixinnodetypes xmlns:dcr="http://www.day.com/jcr/webdav/1.0">'; foreach ($nativeValue as $value) { $body .= '<dcr:nodetype><dcr:nodetypename>' . $value . '</dcr:nodetypename></dcr:nodetype>'; } $body .= '</dcr:mixinnodetypes>' . '</D:prop>' . '</D:set>' . '</D:propertyupdate>'; } elseif (is_array($nativeValue)) { $body = '<?xml version="1.0" encoding="UTF-8"?>' . '<jcr:values xmlns:jcr="http://www.day.com/jcr/webdav/1.0">'; foreach ($nativeValue as $value) { $body .= '<jcr:value jcr:type="' . $type . '">' . $this->propertyToXmlString($value, $type) . '</jcr:value>'; } $body .= '</jcr:values>'; } else { $body = $this->propertyToRawString($nativeValue, $type); $request->setContentType('jcr-value/' . strtolower($type)); } $request->setBody($body); $request->execute(); return true; }
/** * Construct the test data for the testDynamicRebinding test. * The resulting array is composed of arrays as follow:. * * array(new_property_name, * initial_property_type, initial_property_value, * new_property_type, new_property_value, * name_of_the_getter_to_read_the_new_value) * * @return array */ public function dynamicRebindingProvider() { $typesAndValues = array(PropertyType::STRING => 'abcdefg', PropertyType::URI => 'https://github.com/jackalope/jackalope/wiki', PropertyType::BOOLEAN => true, PropertyType::LONG => 3, PropertyType::DOUBLE => 3.1415926535897, PropertyType::DECIMAL => '3.14', PropertyType::BINARY => 'some binary stuff', PropertyType::DATE => new \DateTime(), PropertyType::NAME => 'jcr:some_name', PropertyType::PATH => '/some/valid/path', PropertyType::WEAKREFERENCE => $this->referenceable_node_uuid, PropertyType::REFERENCE => $this->referenceable_node_uuid); $getters = array(PropertyType::STRING => 'getString', PropertyType::URI => 'getString', PropertyType::BOOLEAN => 'getBoolean', PropertyType::LONG => 'getLong', PropertyType::DOUBLE => 'getDouble', PropertyType::DECIMAL => 'getDecimal', PropertyType::BINARY => 'getString', PropertyType::DATE => 'getDate', PropertyType::NAME => 'getString', PropertyType::PATH => 'getString', PropertyType::WEAKREFERENCE => 'getString', PropertyType::REFERENCE => 'getString'); $provider = array(); foreach ($typesAndValues as $sourceKey => $sourceVal) { foreach ($typesAndValues as $destKey => $destVal) { if ($sourceKey !== $destKey) { $propName = 'dynRebinding_' . PropertyType::nameFromValue($sourceKey) . '_To_' . PropertyType::nameFromValue($destKey); $provider[] = array($propName, $sourceKey, $sourceVal, $destKey, $destVal, $getters[$destKey]); } } } return $provider; }