Exemplo n.º 1
0
 /**
  * Test search InternalSkipToeknInfo::GetIndexOfFirstEntryInNextPage function
  */
 public function testGetIndexOfFirstEntryInNextPage2()
 {
     try {
         $northWindMetadata = CreateNorthWindMetadata1::Create();
         $configuration = new DataServiceConfiguration($northWindMetadata);
         $configuration->setEntitySetAccessRule('*', EntitySetRights::ALL);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, null, $configuration, false);
         $resourceSetWrapper = $metaQueryProverWrapper->resolveResourceSet('Orders');
         $resourceType = $resourceSetWrapper->getResourceType();
         $orderBy = 'ShipName asc, Freight';
         //Note: library will add prim key as last sort key
         $orderBy .= ', OrderID';
         $qp = new NorthWindQueryProvider1();
         $orders = $qp->getResourceSet($resourceSetWrapper->getResourceSet());
         $internalOrderByInfo = OrderByParser::parseOrderByClause($resourceSetWrapper, $resourceType, $orderBy, $metaQueryProverWrapper);
         $compFun = $internalOrderByInfo->getSorterFunction();
         $fun = $compFun->getReference();
         usort($orders, $fun);
         $numRecords = count($orders);
         //-----------------------------------------------------------------
         //Search with a key that exactly matches
         $skipToken = utf8_decode(urldecode("'Antonio%20Moreno%20Taquer%C3%ADa',22.0000M,10365"));
         $skipToken = urldecode($skipToken);
         $internalSkipTokenInfo = SkipTokenParser::parseSkipTokenClause($resourceType, $internalOrderByInfo, $skipToken);
         $nextIndex = $internalSkipTokenInfo->getIndexOfFirstEntryInTheNextPage($orders);
         $this->assertTrue($nextIndex > 1);
         $this->assertTrue($nextIndex < $numRecords);
         //$nextIndex is the index of order record next to the searched record
         $this->assertEquals($orders[$nextIndex - 1]->OrderID, 10365);
         $this->assertEquals($orders[$nextIndex - 1]->Freight, 22.0);
         //-----------------------------------------------------------------
         //Search with a key that partially matches, in the DB there is no
         //order with ShipName 'An', but there are records start with
         //'An', so partial match, since its a parial match other two
         //key wont be used for comparsion
         $skipToken = "'An',22.0000M,10365";
         $internalSkipTokenInfo = SkipTokenParser::parseSkipTokenClause($resourceType, $internalOrderByInfo, $skipToken);
         $nextIndex = $internalSkipTokenInfo->getIndexOfFirstEntryInTheNextPage($orders);
         $this->assertTrue($nextIndex > 1);
         $this->assertTrue($nextIndex < $numRecords);
         //Make sure this is the most matching record by comparing with previous record
         $prevOrder = $orders[$nextIndex - 1];
         $r = strcmp($prevOrder->ShipName, $orders[$nextIndex]->ShipName);
         $this->assertTrue($r < 0);
         //Make sure this is the most matching record by comparing with next record
         $nextOrder = $orders[$nextIndex + 1];
         $r = strcmp($nextOrder->ShipName, $orders[$nextIndex]->ShipName);
         $this->assertTrue($r >= 0);
         //-----------------------------------------------------------------
         //Search with a key that does not exists
         $skipToken = "'XXX',11,10365";
         $internalSkipTokenInfo = SkipTokenParser::parseSkipTokenClause($resourceType, $internalOrderByInfo, $skipToken);
         $nextIndex = $internalSkipTokenInfo->getIndexOfFirstEntryInTheNextPage($orders);
         $this->assertTrue($nextIndex == -1);
         //-----------------------------------------------------------------
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised.' . $exception->getMessage());
     }
 }
Exemplo n.º 2
0
 /**
  * Gets the namespace of the given resource type, 
  * if it is null, then default to the container namespace. 
  * 
  * @param ResourceType $resourceType The resource type
  * 
  * @return string The namespace of the resource type.
  */
 protected function getResourceTypeNamespace(ResourceType $resourceType)
 {
     $resourceTypeNamespace = $resourceType->getNamespace();
     if (empty($resourceTypeNamespace)) {
         $resourceTypeNamespace = $this->metadataQueryproviderWrapper->getContainerNamespace();
     }
     return $resourceTypeNamespace;
 }
Exemplo n.º 3
0
 /**
  * Write the service document in Atom format.
  * 
  * @param Object &$dummy Dummy object
  * 
  * @return string
  */
 public function writeRequest(&$dummy)
 {
     $this->_xmlWriter = new \XMLWriter();
     $this->_xmlWriter->openMemory();
     $this->_xmlWriter->startElementNs(null, ODataConstants::ATOM_PUBLISHING_SERVICE_ELEMENT_NAME, ODataConstants::APP_NAMESPACE);
     $this->_xmlWriter->writeAttributeNs(ODataConstants::XML_NAMESPACE_PREFIX, ODataConstants::XML_BASE_ATTRIBUTE_NAME, null, $this->_baseUri);
     $this->_xmlWriter->writeAttributeNs(ODataConstants::XMLNS_NAMESPACE_PREFIX, self::ATOM_NAMESPACE_PREFIX, null, ODataConstants::ATOM_NAMESPACE);
     $this->_xmlWriter->writeAttributeNs(ODataConstants::XMLNS_NAMESPACE_PREFIX, self::APP_NAMESPACE_PREFIX, null, ODataConstants::APP_NAMESPACE);
     $this->_xmlWriter->startElement(ODataConstants::ATOM_PUBLISHING_WORKSPACE_ELEMNT_NAME);
     $this->_xmlWriter->startElementNs(self::ATOM_NAMESPACE_PREFIX, ODataConstants::ATOM_TITLE_ELELMET_NAME, null);
     $this->_xmlWriter->text(ODataConstants::ATOM_PUBLISHING_WORKSPACE_DEFAULT_VALUE);
     $this->_xmlWriter->endElement();
     foreach ($this->_metadataQueryproviderWrapper->getResourceSets() as $resourceSetWrapper) {
         //start collection node
         $this->_xmlWriter->startElement(ODataConstants::ATOM_PUBLISHING_COLLECTION_ELEMENT_NAME);
         $this->_xmlWriter->writeAttribute(ODataConstants::ATOM_HREF_ATTRIBUTE_NAME, $resourceSetWrapper->getName());
         //start title node
         $this->_xmlWriter->startElementNs(self::ATOM_NAMESPACE_PREFIX, ODataConstants::ATOM_TITLE_ELELMET_NAME, null);
         $this->_xmlWriter->text($resourceSetWrapper->getName());
         //end title node
         $this->_xmlWriter->endElement();
         //end collection node
         $this->_xmlWriter->endElement();
     }
     //End workspace and service nodes
     $this->_xmlWriter->endElement();
     $this->_xmlWriter->endElement();
     $serviceDocumentInAtom = $this->_xmlWriter->outputMemory(true);
     return $serviceDocumentInAtom;
 }
 public function testWriteMetadata()
 {
     $northWindMetadata = CreateNorthWindMetadata1::Create();
     $configuration = new DataServiceConfiguration($northWindMetadata);
     $configuration->setEntitySetAccessRule("*", EntitySetRights::ALL);
     $configuration->setMaxDataServiceVersion(DataServiceProtocolVersion::V3);
     $northWindQuery = new NorthWindQueryProvider1();
     $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, $northWindQuery, $configuration, false);
     $metadataWriter = new MetadataWriter($metaQueryProverWrapper);
     $metadata = $metadataWriter->writeMetadata();
     $this->assertNotNull($metadata);
     $this->assertEquals($metaQueryProverWrapper->getContainerName(), 'NorthWindEntities');
     $this->assertEquals($metaQueryProverWrapper->getContainerNamespace(), 'NorthWind');
     $this->assertStringStartsWith('<edmx:Edmx Version="1.0"', $metadata);
     $customerResourceSet = $metaQueryProverWrapper->resolveResourceSet('Customers');
     $this->assertEquals($customerResourceSet->getName(), 'Customers');
     $this->assertEquals($customerResourceSet->getResourceType()->getName(), 'Customer');
     $customerEntityType = $metaQueryProverWrapper->resolveResourceType('Customer');
     $this->assertEquals($customerEntityType->getResourceTypeKind(), ResourceTypeKind::ENTITY);
 }
Exemplo n.º 5
0
 /**
  * Build 'Projection Tree' from the given expand path segments
  * 
  * @param array(array(string)) $expandPathSegments Collection of expand 
  *                                                 paths.
  * 
  * @return void
  * 
  * @throws ODataException If any error occurs while processing the expand
  *                        path segments.
  */
 private function _buildProjectionTree($expandPathSegments)
 {
     foreach ($expandPathSegments as $expandSubPathSegments) {
         $currentNode = $this->_rootProjectionNode;
         foreach ($expandSubPathSegments as $expandSubPathSegment) {
             $resourceSetWrapper = $currentNode->getResourceSetWrapper();
             $resourceType = $currentNode->getResourceType();
             $resourceProperty = $resourceType->tryResolvePropertyTypeByName($expandSubPathSegment);
             if (is_null($resourceProperty)) {
                 ODataException::createSyntaxError(Messages::expandProjectionParserPropertyNotFound($resourceType->getFullName(), $expandSubPathSegment, false));
             } else {
                 if ($resourceProperty->getTypeKind() != ResourceTypeKind::ENTITY) {
                     ODataException::createBadRequestError(Messages::expandProjectionParserExpandCanOnlyAppliedToEntity($resourceType->getFullName(), $expandSubPathSegment));
                 }
             }
             $resourceSetWrapper = $this->_providerWrapper->getResourceSetWrapperForNavigationProperty($resourceSetWrapper, $resourceType, $resourceProperty);
             if (is_null($resourceSetWrapper)) {
                 ODataException::createBadRequestError(Messages::badRequestInvalidPropertyNameSpecified($resourceType->getFullName(), $expandSubPathSegment));
             }
             $singleResult = $resourceProperty->isKindOf(ResourcePropertyKind::RESOURCE_REFERENCE);
             $resourceSetWrapper->checkResourceSetRightsForRead($singleResult);
             $pageSize = $resourceSetWrapper->getResourceSetPageSize();
             $internalOrderByInfo = null;
             if ($pageSize != 0 && !$singleResult) {
                 $this->_rootProjectionNode->setPagedExpandedResult(true);
                 $rt = $resourceSetWrapper->getResourceType();
                 //assert($rt != null)
                 $keys = array_keys($rt->getKeyProperties());
                 //assert(!empty($keys))
                 $orderBy = null;
                 foreach ($keys as $key) {
                     $orderBy = $orderBy . $key . ', ';
                 }
                 $orderBy = rtrim($orderBy, ', ');
                 try {
                     $internalOrderByInfo = OrderByParser::parseOrderByClause($resourceSetWrapper, $rt, $orderBy, $this->_providerWrapper);
                 } catch (ODataException $odataException) {
                     throw $odataException;
                 }
             }
             $node = $currentNode->findNode($expandSubPathSegment);
             if (is_null($node)) {
                 $maxResultCount = $this->_providerWrapper->getConfiguration()->getMaxResultsPerCollection();
                 $node = new ExpandedProjectionNode($expandSubPathSegment, $resourceProperty, $resourceSetWrapper, $internalOrderByInfo, null, $pageSize == 0 ? null : $pageSize, $maxResultCount == PHP_INT_MAX ? null : $maxResultCount);
                 $currentNode->addNode($node);
             }
             $currentNode = $node;
         }
     }
 }
Exemplo n.º 6
0
 /**
  * Write entity container 
  * 
  * @return nothing
  */
 private function _writeEntityContainer()
 {
     $this->_iOdataWriter->startElement(ODataConstants::ENTITY_CONTAINER);
     $this->_iOdataWriter->writeAttribute(ODataConstants::NAME, $this->_metadataQueryproviderWrapper->getContainerName());
     $this->_iOdataWriter->writeAttributeNs(ODataConstants::ODATA_METADATA_NAMESPACE_PREFIX, ODataConstants::ISDEFAULT_ENTITY_CONTAINER_ATTRIBUTE, null, "true");
     foreach ($this->_metadataManager->getResourceSets() as $resourceSet) {
         $this->_iOdataWriter->startElement(ODataConstants::ENTITY_SET);
         $this->_iOdataWriter->writeAttribute(ODataConstants::NAME, $resourceSet->getName());
         $this->_iOdataWriter->writeAttribute(ODataConstants::ENTITY_TYPE, $resourceSet->getResourceType()->getFullName());
         $this->_iOdataWriter->endElement();
     }
     $this->_writeAssociationSets();
     $this->_iOdataWriter->endElement();
 }
Exemplo n.º 7
0
 /**
  * Create SegmentDescriptor for the first segment
  * 
  * @param string  $segmentIdentifier The identifier part of the 
  *                                   first segment
  * @param string  $keyPredicate      The predicate part of the first
  *                                   segment if any else NULL     
  * @param boolean $checkRights       Whether to check the rights on 
  *                                   this segment
  * 
  * @return SegmentDescriptor Descriptor for the first segment
  * 
  * @throws ODataException Exception if any validation fails
  */
 private function _createFirstSegmentDescriptor($segmentIdentifier, $keyPredicate, $checkRights)
 {
     $descriptor = new SegmentDescriptor();
     $descriptor->setIdentifier($segmentIdentifier);
     if ($segmentIdentifier === ODataConstants::URI_METADATA_SEGMENT) {
         $this->_assertion(is_null($keyPredicate));
         $descriptor->setTargetKind(RequestTargetKind::METADATA);
         return $descriptor;
     }
     if ($segmentIdentifier === ODataConstants::URI_BATCH_SEGMENT) {
         $this->_assertion(is_null($keyPredicate));
         $descriptor->setTargetKind(RequestTargetKind::BATCH);
         return $descriptor;
     }
     if ($segmentIdentifier === ODataConstants::URI_COUNT_SEGMENT) {
         ODataException::createBadRequestError(Messages::segmentParserSegmentNotAllowedOnRoot(ODataConstants::URI_COUNT_SEGMENT));
     }
     if ($segmentIdentifier === ODataConstants::URI_LINK_SEGMENT) {
         ODataException::createBadRequestError(Messages::segmentParserSegmentNotAllowedOnRoot(ODataConstants::URI_LINK_SEGMENT));
     }
     $resourceSetWrapper = $this->_providerWrapper->resolveResourceSet($segmentIdentifier);
     if ($resourceSetWrapper === null) {
         ODataException::createResourceNotFoundError($segmentIdentifier);
     }
     $descriptor->setTargetResourceSetWrapper($resourceSetWrapper);
     $descriptor->setTargetResourceType($resourceSetWrapper->getResourceType());
     $descriptor->setTargetSource(RequestTargetSource::ENTITY_SET);
     $descriptor->setTargetKind(RequestTargetKind::RESOURCE);
     if ($keyPredicate !== null) {
         $keyDescriptor = $this->_createKeyDescriptor($segmentIdentifier . '(' . $keyPredicate . ')', $resourceSetWrapper->getResourceType(), $keyPredicate);
         $descriptor->setKeyDescriptor($keyDescriptor);
         if (!$keyDescriptor->isEmpty()) {
             $descriptor->setSingleResult(true);
         }
     }
     if ($checkRights) {
         $resourceSetWrapper->checkResourceSetRightsForRead($descriptor->isSingleResult());
     }
     return $descriptor;
 }
 /**
  * Write the service document in JSON format.
  * 
  * @param Object &$dummy Dummy object
  * 
  * @return string
  */
 public function writeRequest(&$dummy)
 {
     // { "d" :
     $this->_writer->startObjectScope();
     $this->_writer->writeDataWrapper();
     // {
     $this->_writer->startObjectScope();
     // "EntitySets"
     $this->_writer->writeName(ODataConstants::ENTITY_SET);
     // [
     $this->_writer->startArrayScope();
     foreach ($this->_metadataQueryproviderWrapper->getResourceSets() as $resourceSetWrapper) {
         $this->_writer->writeValue($resourceSetWrapper->getName());
     }
     // ]
     $this->_writer->endScope();
     // }
     $this->_writer->endScope();
     // }
     $this->_writer->endScope();
     //result
     $serviceDocumentInJson = $this->_writer->getJsonOutput();
     return $serviceDocumentInJson;
 }
Exemplo n.º 9
0
 /**
  * Test whether order by parser identify and remove path duplication
  */
 public function testOrderByWithPathDuplication()
 {
     try {
         $northWindMetadata = CreateNorthWindMetadata3::Create();
         $configuration = new DataServiceConfiguration($northWindMetadata);
         $configuration->setEntitySetAccessRule('*', EntitySetRights::ALL);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, null, $configuration, false);
         $resourceSetWrapper = $metaQueryProverWrapper->resolveResourceSet('Order_Details');
         $resourceType = $resourceSetWrapper->getResourceType();
         $orderBy = 'Order/Price desc, Product/ProductName asc, Order/Price asc';
         $internalOrderInfo = OrderByParser::parseOrderByClause($resourceSetWrapper, $resourceType, $orderBy, $metaQueryProverWrapper);
         //The orderby path Order/Price appears twice, but parser will consider only first path
         $orderByInfo = $internalOrderInfo->getOrderByInfo();
         //There are navigation (resource reference) properties in the orderby path so getNavigationPropertiesUsed should
         //not be null
         $naviUsed = $orderByInfo->getNavigationPropertiesUsed();
         $this->assertFalse(is_null($naviUsed));
         //3 path segment are there, but last one is duplicate of first one, so parser removes last one
         $this->assertEquals(count($naviUsed), 2);
         $this->assertTrue(is_array($naviUsed[0]));
         $this->assertTrue(is_array($naviUsed[1]));
         //one navgations used in first orderby 'Order'
         $this->assertEquals(count($naviUsed[0]), 1);
         //one navgations used in second orderby 'Prodcut'
         $this->assertEquals(count($naviUsed[1]), 1);
         $this->assertEquals($naviUsed[0][0]->getName(), 'Order');
         $this->assertEquals($naviUsed[1][0]->getName(), 'Product');
         $orderByPathSegments = $orderByInfo->getOrderByPathSegments();
         $this->assertEquals(count($orderByPathSegments), 2);
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised' . $exception->getMessage());
     }
 }
Exemplo n.º 10
0
 /**
  * Gets resource sets which are visible
  * 
  * @return array(ResourceSetWrapper)
  */
 public function getResourceSets()
 {
     return $this->_metadataQueryproviderWrapper->getResourceSets();
 }
Exemplo n.º 11
0
 /**
  * Build 'OrderBy Tree' from the given orderby path segments, also build 
  * comparsion function for each path segment.
  * 
  * @param array(array) &$ordeyByPathSegments Collection of orderby path segments,
  *                                           this is passed by reference
  *                                           since we need this function to 
  *                                           modify this array in two cases:
  *                                           1. if asc or desc present, then the 
  *                                              corrosponding sub path segment 
  *                                              should be removed
  *                                           2. remove duplicate orderby path 
  *                                              segment
  * 
  * @return void
  * 
  * @throws ODataException If any error occurs while processing the orderby path 
  *                        segments
  */
 private function _buildOrderByTree(&$ordeyByPathSegments)
 {
     foreach ($ordeyByPathSegments as $index1 => &$ordeyBySubPathSegments) {
         $currentNode = $this->_rootOrderByNode;
         $currentObject = $this->_dummyObject;
         $ascending = true;
         $subPathCount = count($ordeyBySubPathSegments);
         // Check sort order is specified in the path, if so set a
         // flag and remove that segment
         if ($subPathCount > 1) {
             if ($ordeyBySubPathSegments[$subPathCount - 1] === '*desc') {
                 $ascending = false;
                 unset($ordeyBySubPathSegments[$subPathCount - 1]);
                 $subPathCount--;
             } else {
                 if ($ordeyBySubPathSegments[$subPathCount - 1] === '*asc') {
                     unset($ordeyBySubPathSegments[$subPathCount - 1]);
                     $subPathCount--;
                 }
             }
         }
         $ancestors = array($this->_rootOrderByNode->getResourceSetWrapper()->getName());
         foreach ($ordeyBySubPathSegments as $index2 => $orderBySubPathSegment) {
             $isLastSegment = $index2 == $subPathCount - 1;
             $resourceSetWrapper = null;
             $resourceType = $currentNode->getResourceType();
             $resourceProperty = $resourceType->tryResolvePropertyTypeByName($orderBySubPathSegment);
             if (is_null($resourceProperty)) {
                 ODataException::createSyntaxError(Messages::orderByParserPropertyNotFound($resourceType->getFullName(), $orderBySubPathSegment));
             }
             if ($resourceProperty->isKindOf(ResourcePropertyKind::BAG)) {
                 ODataException::createBadRequestError(Messages::orderByParserBagPropertyNotAllowed($resourceProperty->getName()));
             } else {
                 if ($resourceProperty->isKindOf(ResourcePropertyKind::PRIMITIVE)) {
                     if (!$isLastSegment) {
                         ODataException::createBadRequestError(Messages::orderByParserPrimitiveAsIntermediateSegment($resourceProperty->getName()));
                     }
                     $type = $resourceProperty->getInstanceType();
                     if ($type instanceof Binary) {
                         ODataException::createBadRequestError(Messages::orderbyParserSortByBinaryPropertyNotAllowed($resourceProperty->getName()));
                     }
                 } else {
                     if ($resourceProperty->getKind() == ResourcePropertyKind::RESOURCESET_REFERENCE || $resourceProperty->getKind() == ResourcePropertyKind::RESOURCE_REFERENCE) {
                         $this->_assertion($currentNode instanceof OrderByRootNode || $currentNode instanceof OrderByNode);
                         $resourceSetWrapper = $currentNode->getResourceSetWrapper();
                         $this->_assertion(!is_null($resourceSetWrapper));
                         $resourceSetWrapper = $this->_providerWrapper->getResourceSetWrapperForNavigationProperty($resourceSetWrapper, $resourceType, $resourceProperty);
                         if (is_null($resourceSetWrapper)) {
                             ODataException::createBadRequestError(Messages::badRequestInvalidPropertyNameSpecified($resourceType->getFullName(), $orderBySubPathSegment));
                         }
                         if ($resourceProperty->getKind() == ResourcePropertyKind::RESOURCESET_REFERENCE) {
                             ODataException::createBadRequestError(Messages::orderbyParserResourceSetReferenceNotAllowed($resourceProperty->getName(), $resourceType->getFullName()));
                         }
                         $resourceSetWrapper->checkResourceSetRightsForRead(true);
                         if ($isLastSegment) {
                             ODataException::createBadRequestError(Messages::orderByParserSortByNavigationPropertyIsNotAllowed($resourceProperty->getName()));
                         }
                         $ancestors[] = $orderBySubPathSegment;
                     } else {
                         if ($resourceProperty->isKindOf(ResourcePropertyKind::COMPLEX_TYPE)) {
                             if ($isLastSegment) {
                                 ODataException::createBadRequestError(Messages::orderByParserSortByComplexPropertyIsNotAllowed($resourceProperty->getName()));
                             }
                             $ancestors[] = $orderBySubPathSegment;
                         } else {
                             ODataException::createInternalServerError(Messages::orderByParserUnexpectedPropertyType());
                         }
                     }
                 }
             }
             $node = $currentNode->findNode($orderBySubPathSegment);
             if (is_null($node)) {
                 if ($resourceProperty->isKindOf(ResourcePropertyKind::PRIMITIVE)) {
                     $node = new OrderByLeafNode($orderBySubPathSegment, $resourceProperty, $ascending);
                     $this->_comparisonFunctions[] = $node->buildComparisonFunction($ancestors);
                 } else {
                     if ($resourceProperty->getKind() == ResourcePropertyKind::RESOURCE_REFERENCE) {
                         $node = new OrderByNode($orderBySubPathSegment, $resourceProperty, $resourceSetWrapper);
                         // Initialize this member variable (identified by
                         // $resourceProperty) of parent object.
                         try {
                             $dummyProperty = new \ReflectionProperty($currentObject, $resourceProperty->getName());
                             $object = $resourceProperty->getInstanceType()->newInstance();
                             $dummyProperty->setValue($currentObject, $object);
                             $currentObject = $object;
                         } catch (\ReflectionException $reflectionException) {
                             throw ODataException::createInternalServerError(Messages::orderByParserFailedToAccessOrInitializeProperty($resourceProperty->getName(), $resourceType->getName()));
                         }
                     } else {
                         if ($resourceProperty->getKind() == ResourcePropertyKind::COMPLEX_TYPE) {
                             $node = new OrderByNode($orderBySubPathSegment, $resourceProperty, null);
                             // Initialize this member variable
                             // (identified by $resourceProperty)of parent object.
                             try {
                                 $dummyProperty = new \ReflectionProperty($currentObject, $resourceProperty->getName());
                                 $object = $resourceProperty->getInstanceType()->newInstance();
                                 $dummyProperty->setValue($currentObject, $object);
                                 $currentObject = $object;
                             } catch (\ReflectionException $reflectionException) {
                                 throw ODataException::createInternalServerError(Messages::orderByParserFailedToAccessOrInitializeProperty($resourceProperty->getName(), $resourceType->getName()));
                             }
                         }
                     }
                 }
                 $currentNode->addNode($node);
             } else {
                 try {
                     $dummyProperty = new \ReflectionProperty($currentObject, $resourceProperty->getName());
                     $currentObject = $dummyProperty->getValue($currentObject);
                 } catch (\ReflectionException $reflectionException) {
                     throw ODataException::createInternalServerError(Messages::orderByParserFailedToAccessOrInitializeProperty($resourceProperty->getName(), $resourceType->getName()));
                 }
                 if ($node instanceof OrderByLeafNode) {
                     //remove duplicate orderby path
                     unset($ordeyByPathSegments[$index1]);
                 }
             }
             $currentNode = $node;
         }
     }
 }
Exemplo n.º 12
0
 /**
  * Execute queries for expansion.
  * 
  * @param array(mixed)/mixed &$result Resource(s) whose navigation properties
  *                                    needs to be expanded.
  *
  * @return void
  */
 private function _executeExpansion(&$result)
 {
     $expandedProjectionNodes = $this->_getExpandedProjectionNodes();
     foreach ($expandedProjectionNodes as $expandedProjectionNode) {
         $isCollection = $expandedProjectionNode->getResourceProperty()->getKind() == ResourcePropertyKind::RESOURCESET_REFERENCE;
         $expandedPropertyName = $expandedProjectionNode->getResourceProperty()->getName();
         if (is_array($result)) {
             foreach ($result as $entry) {
                 // Check for null entry
                 if ($isCollection) {
                     $currentResourceSet = $this->_getCurrentResourceSetWrapper()->getResourceSet();
                     $resourceSetOfProjectedProperty = $expandedProjectionNode->getResourceSetWrapper()->getResourceSet();
                     $projectedProperty1 = $expandedProjectionNode->getResourceProperty();
                     $result1 = $this->_provider->getRelatedResourceSet($currentResourceSet, $entry, $resourceSetOfProjectedProperty, $projectedProperty1, null, null, null, null, null);
                     if (!empty($result1)) {
                         $internalOrderByInfo = $expandedProjectionNode->getInternalOrderByInfo();
                         if (!is_null($internalOrderByInfo)) {
                             $orderByFunction = $internalOrderByInfo->getSorterFunction()->getReference();
                             usort($result1, $orderByFunction);
                             unset($internalOrderByInfo);
                             $takeCount = $expandedProjectionNode->getTakeCount();
                             if (!is_null($takeCount)) {
                                 $result1 = array_slice($result1, 0, $takeCount);
                             }
                         }
                         $entry->{$expandedPropertyName} = $result1;
                         $projectedProperty = $expandedProjectionNode->getResourceProperty();
                         $needPop = $this->_pushSegmentForNavigationProperty($projectedProperty);
                         $this->_executeExpansion($result1);
                         $this->_popSegment($needPop);
                     } else {
                         $entry->{$expandedPropertyName} = array();
                     }
                 } else {
                     $currentResourceSet1 = $this->_getCurrentResourceSetWrapper()->getResourceSet();
                     $resourceSetOfProjectedProperty1 = $expandedProjectionNode->getResourceSetWrapper()->getResourceSet();
                     $projectedProperty2 = $expandedProjectionNode->getResourceProperty();
                     $result1 = $this->_provider->getRelatedResourceReference($currentResourceSet1, $entry, $resourceSetOfProjectedProperty1, $projectedProperty2);
                     $entry->{$expandedPropertyName} = $result1;
                     if (!is_null($result1)) {
                         $projectedProperty3 = $expandedProjectionNode->getResourceProperty();
                         $needPop = $this->_pushSegmentForNavigationProperty($projectedProperty3);
                         $this->_executeExpansion($result1);
                         $this->_popSegment($needPop);
                     }
                 }
             }
         } else {
             if ($isCollection) {
                 $currentResourceSet2 = $this->_getCurrentResourceSetWrapper()->getResourceSet();
                 $resourceSetOfProjectedProperty2 = $expandedProjectionNode->getResourceSetWrapper()->getResourceSet();
                 $projectedProperty4 = $expandedProjectionNode->getResourceProperty();
                 $result1 = $this->_provider->getRelatedResourceSet($currentResourceSet2, $result, $resourceSetOfProjectedProperty2, $projectedProperty4, null, null, null, null, null);
                 if (!empty($result1)) {
                     $internalOrderByInfo = $expandedProjectionNode->getInternalOrderByInfo();
                     if (!is_null($internalOrderByInfo)) {
                         $orderByFunction = $internalOrderByInfo->getSorterFunction()->getReference();
                         usort($result1, $orderByFunction);
                         unset($internalOrderByInfo);
                         $takeCount = $expandedProjectionNode->getTakeCount();
                         if (!is_null($takeCount)) {
                             $result1 = array_slice($result1, 0, $takeCount);
                         }
                     }
                     $result->{$expandedPropertyName} = $result1;
                     $projectedProperty7 = $expandedProjectionNode->getResourceProperty();
                     $needPop = $this->_pushSegmentForNavigationProperty($projectedProperty7);
                     $this->_executeExpansion($result1);
                     $this->_popSegment($needPop);
                 } else {
                     $result->{$expandedPropertyName} = array();
                 }
             } else {
                 $currentResourceSet3 = $this->_getCurrentResourceSetWrapper()->getResourceSet();
                 $resourceSetOfProjectedProperty3 = $expandedProjectionNode->getResourceSetWrapper()->getResourceSet();
                 $projectedProperty5 = $expandedProjectionNode->getResourceProperty();
                 $result1 = $this->_provider->getRelatedResourceReference($currentResourceSet3, $result, $resourceSetOfProjectedProperty3, $projectedProperty5);
                 $result->{$expandedPropertyName} = $result1;
                 if (!is_null($result1)) {
                     $projectedProperty6 = $expandedProjectionNode->getResourceProperty();
                     $needPop = $this->_pushSegmentForNavigationProperty($projectedProperty6);
                     $this->_executeExpansion($result1);
                     $this->_popSegment($needPop);
                 }
             }
         }
     }
 }
Exemplo n.º 13
0
 /**
  * Check wrapped resource set's resource type or any of the resource type derived
  * from the this resource type has bag property associated with it.
  * 
  * @param MetadataQueryProviderWrapper $provider Metadata query provider wrapper
  * 
  * @return boolean
  */
 public function hasBagProperty(MetadataQueryProviderWrapper $provider)
 {
     $arrayToDetectLoop = array();
     $hasBagProperty = $this->_resourceSet->getResourceType()->hasBagProperty($arrayToDetectLoop);
     unset($arrayToDetectLoop);
     // This will check only the resource type associated with
     // the resource set, we need to check presence of bag property
     // in resource type which is derived form this resource type also.
     if (!$hasBagProperty) {
         $derivedTypes = $provider->getDerivedTypes($this->_resourceSet->getResourceType());
         if (!is_null($derivedTypes)) {
             foreach ($derivedTypes as $derivedType) {
                 $arrayToDetectLoop = array();
                 if ($derivedType->hasBagProperty($arrayToDetectLoop)) {
                     $hasBagProperty = true;
                     break;
                 }
             }
         }
     }
     return $hasBagProperty;
 }
 /**
  * One can expand a navigation property only if corrosponding resource set is visible
  * 
  */
 public function testExpandWithNonVisibleResourceSet()
 {
     try {
         $northWindMetadata = CreateNorthWindMetadata3::Create();
         $queryProvider = new NorthWindQueryProvider2();
         $configuration = new DataServiceConfiguration($northWindMetadata);
         //Make 'Customers' and 'Orders' visible, make 'Order_Details' invisible
         $configuration->setEntitySetAccessRule('Customers', EntitySetRights::ALL);
         $configuration->setEntitySetAccessRule('Orders', EntitySetRights::ALL);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, $queryProvider, $configuration, false);
         $customersResourceSetWrapper = $metaQueryProverWrapper->resolveResourceSet('Customers');
         $customerResourceType = $customersResourceSetWrapper->getResourceType();
         $exceptionThrown = false;
         try {
             $projectionTree = ExpandProjectionParser::parseExpandAndSelectClause($customersResourceSetWrapper, $customerResourceType, null, null, null, 'Orders/Order_Details', null, $metaQueryProverWrapper);
         } catch (ODataException $odataException) {
             $exceptionThrown = true;
             $this->assertStringEndsWith("(Check the resource set of the navigation property 'Order_Details' is visible)", $odataException->getMessage());
         }
         if (!$exceptionThrown) {
             $this->fail('An expected ODataException for navigation to invisible resource set has not been thrown');
         }
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised' . $exception->getMessage());
     }
 }
 /**
  * If last sub path segment specified in the select clause does not appear in the prjection tree,
  * then parser will create 'ProjectionNode' for them
  */
 public function testPrjectionNodeCreation()
 {
     try {
         $northWindMetadata = CreateNorthWindMetadata3::Create();
         $queryProvider = new NorthWindQueryProvider2();
         $configuration = new DataServiceConfiguration($northWindMetadata);
         $configuration->setEntitySetAccessRule('*', EntitySetRights::ALL);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, $queryProvider, $configuration, false);
         $ordersResourceSetWrapper = $metaQueryProverWrapper->resolveResourceSet('Orders');
         $orderResourceType = $ordersResourceSetWrapper->getResourceType();
         //test selection of properties which is not included in expand clause
         //1 primitve ('Order_Details/UnitPrice') and 1 link to navigation 'Customer'
         $projectionTreeRoot = ExpandProjectionParser::parseExpandAndSelectClause($ordersResourceSetWrapper, $orderResourceType, null, null, null, 'Order_Details', 'Order_Details/UnitPrice, Customer', $metaQueryProverWrapper);
         //expand option is absent
         $this->assertTrue($projectionTreeRoot->isExpansionSpecified());
         //select is applied
         $this->assertTrue($projectionTreeRoot->isSelectionSpecified());
         $this->assertFalse($projectionTreeRoot->canSelectAllImmediateProperties());
         $this->assertFalse($projectionTreeRoot->canSelectAllProperties());
         //there are 2 child nodes for the root
         $this->assertEquals(count($projectionTreeRoot->getChildNodes()), 2);
         //The child nodes one 'ProjectionNode' Customer and one 'ExpandedProjectionNode' for 'Order'
         $childNodes = $projectionTreeRoot->getChildNodes();
         $this->assertTrue(array_key_exists('Order_Details', $childNodes));
         $this->assertTrue(array_key_exists('Customer', $childNodes));
         $this->assertTrue($childNodes['Order_Details'] instanceof ExpandedProjectionNode);
         $this->assertTrue($childNodes['Customer'] instanceof ProjectionNode);
         //'Order_Detials' has a child node
         $childNodes = $childNodes['Order_Details']->getChildNodes();
         $this->assertEquals(count($childNodes), 1);
         $this->assertTrue(array_key_exists('UnitPrice', $childNodes));
         $this->assertTrue($childNodes['UnitPrice'] instanceof ProjectionNode);
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised' . $exception->getMessage());
     }
 }
Exemplo n.º 16
0
 /**
  * test the creation of nextlink from an object.
  * Test building of link with guid sub-value
  */
 public function testCreationOfNextLink4()
 {
     try {
         $northWindMetadata = CreateNorthWindMetadata3::Create();
         $configuration = new DataServiceConfiguration($northWindMetadata);
         $configuration->setEntitySetAccessRule('*', EntitySetRights::ALL);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($northWindMetadata, null, $configuration, false);
         $resourceSetWrapper = $metaQueryProverWrapper->resolveResourceSet('Customers');
         $resourceType = $resourceSetWrapper->getResourceType();
         $orderBy = 'CustomerID, CustomerGuid';
         $internalOrderByInfo = OrderByParser::parseOrderByClause($resourceSetWrapper, $resourceType, $orderBy, $metaQueryProverWrapper);
         $skipToken = "null, guid'05b242e752eb46bd8f0e6568b72cd9a5'";
         $internalSkipTokenInfo = SkipTokenParser::parseSkipTokenClause($resourceType, $internalOrderByInfo, $skipToken);
         $keyObject = $internalSkipTokenInfo->getKeyObject();
         $lastObject = new Customer2();
         $lastObject->CustomerID = 'ABC';
         $lastObject->CustomerGuid = '{05b242e7-52eb-46bd-8f0e-6568b72cd9a5}';
         $nextLink = $internalSkipTokenInfo->buildNextPageLink($lastObject);
         $this->assertEquals($nextLink, "'ABC', guid'%7B05b242e7-52eb-46bd-8f0e-6568b72cd9a5%7D'");
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised.' . $exception->getMessage());
     }
 }
 public function testGetTypes2()
 {
     try {
         //Try to get all resource sets with non of the resouce sets are visible
         $configuration = null;
         $metadataProvider = $this->_createMetadataAndConfiguration2($configuration);
         $metaQueryProverWrapper = new MetadataQueryProviderWrapper($metadataProvider, null, $configuration, false);
         $exceptionThrown = false;
         try {
             $metaQueryProverWrapper->getTypes();
         } catch (ODataException $exception) {
             $exceptionThrown = true;
             $this->assertEquals($exception->getMessage(), 'More than one entity type with the name \'Order\' was found. Entity type names must be unique.');
         }
         if (!$exceptionThrown) {
             $this->fail('An expected ODataException for entity type name repetition has not been thrown');
         }
     } catch (\Exception $exception) {
         $this->fail('An unexpected Exception has been raised' . $exception->getMessage());
     }
 }