示例#1
0
 /**
  * Parse and generate expression from the the given odata expression.
  *
  * 
  * @param string              $text               The text expression to parse
  * @param ResourceType        $resourceType       The resource type in which
  * @param IExpressionProvider $expressionProvider Implementation of IExpressionProvider
  * 
  * @return FilterInfo
  * 
  * @throws ODataException If any error occurs while parsing the odata expression or building the php/custom expression.
  *
  */
 public static function parseExpression2($text, ResourceType $resourceType, \POData\Providers\Expression\IExpressionProvider $expressionProvider)
 {
     $expressionParser2 = new ExpressionParser2($text, $resourceType, $expressionProvider instanceof PHPExpressionProvider);
     $expressionTree = $expressionParser2->parseFilter();
     $expressionAsString = null;
     $expressionProvider->setResourceType($resourceType);
     $expressionProcessor = new ExpressionProcessor($expressionProvider);
     try {
         $expressionAsString = $expressionProcessor->processExpression($expressionTree);
     } catch (\InvalidArgumentException $invalidArgumentException) {
         throw ODataException::createInternalServerError($invalidArgumentException->getMessage());
     }
     return new FilterInfo($expressionParser2->_navigationPropertiesUsedInTheExpression, $expressionAsString);
 }
 /**
  * Parse the astoria filter expression, generate the same expression as PHP expression,
  * retrieve only the entries which satisfies this expression.
  * 
  * @param string         $astoriaFilter
  * @param ResourceType    $resourceType
  * @param array<objects> $entries
  * 
  * @return array<objects>
  */
 private function executeExpression($astoriaFilter, $resourceType, $entries)
 {
     //Parse the Astoria filter query option to expression tree
     $parser = new ExpressionParser2($astoriaFilter, $resourceType, true);
     $expressionTree = $parser->parseFilter();
     //emit the PHP expression corresponds to Astoria filter query
     $expressionProcessor = new ExpressionProcessor(new \POData\Providers\Expression\PHPExpressionProvider('$lt'));
     $phpExpression = $expressionProcessor->processExpression($expressionTree);
     //create an anonymous function with the generated PHP expression in if condition
     $fun = create_function('$lt', 'if(' . $phpExpression . ') { return true; } else { return false;}');
     $result = array();
     foreach ($entries as $lt) {
         //Filter out only the entries which satisfies the condition
         if ($fun($lt)) {
             $result[] = $lt;
         }
     }
     return $result;
 }
 public function testParseExpression2()
 {
     $expressionProvider = new PHPExpressionProvider('$lt');
     $filterExpression = 'UnitPrice ge 6';
     $resourceType = $this->_northWindMetadata->resolveResourceSet('Order_Details')->getResourceType();
     $filterInfo = ExpressionParser2::parseExpression2($filterExpression, $resourceType, $expressionProvider);
     $this->assertTrue(!is_null($filterInfo));
     //There are no navigation properties in the expression so should be empty.
     $this->assertEquals(array(), $filterInfo->getNavigationPropertiesUsed());
     $this->assertEquals('(!(is_null($lt->UnitPrice)) && ($lt->UnitPrice >= 6))', $filterInfo->getExpressionAsString());
     $filterExpression = 'Order/Customer/CustomerID eq \'ANU\' or Product/ProductID gt 123 and UnitPrice ge 6';
     $filterInfo = ExpressionParser2::parseExpression2($filterExpression, $resourceType, $expressionProvider);
     $this->assertTrue(!is_null($filterInfo));
     $navigationsUsed = $filterInfo->getNavigationPropertiesUsed();
     $this->assertTrue(!is_null($navigationsUsed));
     $this->assertTrue(is_array($navigationsUsed));
     $this->assertEquals(count($navigationsUsed), 2);
     //Order/Customer
     $this->assertTrue(is_array($navigationsUsed[0]));
     $this->assertEquals(count($navigationsUsed[0]), 2);
     //Product
     $this->assertTrue(is_array($navigationsUsed[1]));
     $this->assertEquals(count($navigationsUsed[1]), 1);
     //Verify 'Order/Customer'
     $this->assertTrue(is_object($navigationsUsed[0][0]));
     $this->assertTrue(is_object($navigationsUsed[0][1]));
     $this->assertTrue($navigationsUsed[0][0] instanceof ResourceProperty);
     $this->assertTrue($navigationsUsed[0][1] instanceof ResourceProperty);
     $this->assertEquals($navigationsUsed[0][0]->getName(), 'Order');
     $this->assertEquals($navigationsUsed[0][1]->getName(), 'Customer');
     //Verify 'Product'
     $this->assertTrue(is_object($navigationsUsed[1][0]));
     $this->assertTrue($navigationsUsed[1][0] instanceof ResourceProperty);
     $this->assertEquals($navigationsUsed[1][0]->getName(), 'Product');
     $filterExpression = 'Customer/Address/LineNumber add 4 eq 8';
     $resourceType = $this->_northWindMetadata->resolveResourceSet('Orders')->getResourceType();
     $filterInfo = ExpressionParser2::parseExpression2($filterExpression, $resourceType, $expressionProvider);
     $this->assertTrue(!is_null($filterInfo));
     $navigationsUsed = $filterInfo->getNavigationPropertiesUsed();
     //Customer
     $this->assertTrue(!is_null($navigationsUsed));
     $this->assertTrue(is_array($navigationsUsed));
     $this->assertEquals(count($navigationsUsed), 1);
     $this->assertTrue(is_array($navigationsUsed[0]));
     $this->assertEquals(count($navigationsUsed[0]), 1);
     //Verify 'Customer'
     $this->assertTrue(is_object($navigationsUsed[0][0]));
     $this->assertTrue($navigationsUsed[0][0] instanceof ResourceProperty);
     $this->assertEquals($navigationsUsed[0][0]->getName(), 'Customer');
     //Test with property acess expression in function call
     $filterExpression = 'replace(Customer/CustomerID, \'LFK\', \'RTT\') eq \'ARTTI\'';
     $filterInfo = ExpressionParser2::parseExpression2($filterExpression, $resourceType, $expressionProvider);
     $this->assertTrue(!is_null($filterInfo));
     $navigationsUsed = $filterInfo->getNavigationPropertiesUsed();
     //Customer
     $this->assertTrue(!is_null($navigationsUsed));
     $this->assertTrue(is_array($navigationsUsed));
     $this->assertEquals(count($navigationsUsed), 1);
     $this->assertTrue(is_array($navigationsUsed[0]));
     $this->assertEquals(count($navigationsUsed[0]), 1);
     //Verify 'Customer'
     $this->assertTrue(is_object($navigationsUsed[0][0]));
     $this->assertTrue($navigationsUsed[0][0] instanceof ResourceProperty);
     $this->assertEquals($navigationsUsed[0][0]->getName(), 'Customer');
 }
示例#4
0
 /**
  * Process the $filter option in the request and update request decription.
  * 
  * @return void
  * 
  * @throws ODataException Throws error in the following cases:
  *                          (1) If $filter cannot be applied to the 
  *                              resource targeted by the request uri
  *                          (2) If any error occured while parsing and
  *                              translating the odata $filter expression
  *                              to expression tree
  *                          (3) If any error occured while generating
  *                              php expression from expression tree
  */
 private function _processFilter()
 {
     $filter = $this->service->getHost()->getQueryStringItem(ODataConstants::HTTPQUERY_STRING_FILTER);
     if (is_null($filter)) {
         return;
     }
     $kind = $this->request->getTargetKind();
     if (!($kind == TargetKind::RESOURCE() || $kind == TargetKind::COMPLEX_OBJECT() || $this->request->queryType == QueryType::COUNT())) {
         throw ODataException::createBadRequestError(Messages::queryProcessorQueryFilterOptionNotApplicable());
     }
     $resourceType = $this->request->getTargetResourceType();
     $expressionProvider = $this->service->getProvidersWrapper()->getExpressionProvider();
     $filterInfo = ExpressionParser2::parseExpression2($filter, $resourceType, $expressionProvider);
     $this->request->setFilterInfo($filterInfo);
 }