示例#1
0
 /**
  * Serialize the requested resource.
  * 
  * @param RequestDescription &$requestDescription The description of the request 
  *                                                submitted by the client.
  * @param UriProcessor       &$uriProcessor       Reference to the uri processor.
  * 
  * @return void
  */
 protected function serializeResult(RequestDescription &$requestDescription, UriProcessor &$uriProcessor)
 {
     $isETagHeaderAllowed = $requestDescription->isETagHeaderAllowed();
     if ($this->_dataServiceConfiguration->getValidateETagHeader() && !$isETagHeaderAllowed) {
         if (!is_null($this->_dataServiceHost->getRequestIfMatch()) || !is_null($this->_dataServiceHost->getRequestIfNoneMatch())) {
             ODataException::createBadRequestError(Messages::dataServiceETagCannotBeSpecified($this->getHost()->getAbsoluteRequestUri()->getUrlAsString()));
         }
     }
     $responseContentType = null;
     $responseFormat = self::getResponseFormat($requestDescription, $uriProcessor, $this, $responseContentType);
     $odataModelInstance = null;
     $hasResponseBody = true;
     // Execution required at this point if request target to any resource
     // other than
     // (1) media resource - For Media resource 'getResponseFormat' already
     //     performed execution
     // (2) metadata - internal resource
     // (3) service directory - internal resource
     if ($requestDescription->needExecution()) {
         $uriProcessor->execute();
         $objectModelSerializer = new ObjectModelSerializer($this, $requestDescription);
         if (!$requestDescription->isSingleResult()) {
             // Code path for collection (feed or links)
             $entryObjects = $requestDescription->getTargetResult();
             self::assert(!is_null($entryObjects) && is_array($entryObjects), '!is_null($entryObjects) && is_array($entryObjects)');
             // If related resource set is empty for an entry then we should
             // not throw error instead response must be empty feed or empty links
             if ($requestDescription->isLinkUri()) {
                 $odataModelInstance = $objectModelSerializer->writeUrlElements($entryObjects);
                 self::assert($odataModelInstance instanceof \ODataProducer\ObjectModel\ODataURLCollection, '$odataModelInstance instanceof ODataURLCollection');
             } else {
                 $odataModelInstance = $objectModelSerializer->writeTopLevelElements($entryObjects);
                 self::assert($odataModelInstance instanceof \ODataProducer\ObjectModel\ODataFeed, '$odataModelInstance instanceof ODataFeed');
             }
         } else {
             // Code path for entry, complex, bag, resource reference link,
             // primitive type or primitive value
             $result = $requestDescription->getTargetResult();
             $requestTargetKind = $requestDescription->getTargetKind();
             if ($requestDescription->isLinkUri()) {
                 // In the query 'Orders(1245)/$links/Customer', the targetted
                 // Customer might be null
                 if (is_null($result)) {
                     ODataException::createResourceNotFoundError($requestDescription->getIdentifier());
                 }
                 $odataModelInstance = $objectModelSerializer->writeUrlElement($result);
             } else {
                 if ($requestTargetKind == RequestTargetKind::RESOURCE) {
                     if (!is_null($this->_dataServiceHost->getRequestIfMatch()) && !is_null($this->_dataServiceHost->getRequestIfNoneMatch())) {
                         ODataException::createBadRequestError(Messages::dataServiceBothIfMatchAndIfNoneMatchHeaderSpecified());
                     }
                     // handle entry resource
                     $needToSerializeResponse = true;
                     $targetResourceType = $requestDescription->getTargetResourceType();
                     $eTag = $this->compareETag($result, $targetResourceType, $needToSerializeResponse);
                     if ($needToSerializeResponse) {
                         if (is_null($result)) {
                             // In the query 'Orders(1245)/Customer', the targetted
                             // Customer might be null
                             // set status code to 204 => 'No Content'
                             $this->_dataServiceHost->setResponseStatusCode(HttpStatus::CODE_NOCONTENT);
                             $hasResponseBody = false;
                         } else {
                             $odataModelInstance = $objectModelSerializer->writeTopLevelElement($result);
                         }
                     } else {
                         // Resource is not modified so set status code
                         // to 304 => 'Not Modified'
                         $this->_dataServiceHost->setResponseStatusCode(HttpStatus::CODE_NOT_MODIFIED);
                         $hasResponseBody = false;
                     }
                     // if resource has eTagProperty then eTag header needs to written
                     if (!is_null($eTag)) {
                         $this->_dataServiceHost->setResponseETag($eTag);
                     }
                 } else {
                     if ($requestTargetKind == RequestTargetKind::COMPLEX_OBJECT) {
                         $odataModelInstance = new ODataPropertyContent();
                         $targetResourceTypeComplex = $requestDescription->getTargetResourceType();
                         $objectModelSerializer->writeTopLevelComplexObject($result, $requestDescription->getProjectedProperty()->getName(), $targetResourceTypeComplex, $odataModelInstance);
                     } else {
                         if ($requestTargetKind == RequestTargetKind::BAG) {
                             $odataModelInstance = new ODataPropertyContent();
                             $targetResourceTypeBag = $requestDescription->getTargetResourceType();
                             $objectModelSerializer->writeTopLevelBagObject($result, $requestDescription->getProjectedProperty()->getName(), $targetResourceTypeBag, $odataModelInstance);
                         } else {
                             if ($requestTargetKind == RequestTargetKind::PRIMITIVE) {
                                 $odataModelInstance = new ODataPropertyContent();
                                 $projectedProperty = $requestDescription->getProjectedProperty();
                                 $objectModelSerializer->writeTopLevelPrimitive($result, $projectedProperty, $odataModelInstance);
                             } else {
                                 if ($requestTargetKind == RequestTargetKind::PRIMITIVE_VALUE) {
                                     // Code path for primitive value (Since its primitve no need for
                                     // object model serialization)
                                     // Customers('ANU')/CompanyName/$value => string
                                     // Employees(1)/Photo/$value => binary stream
                                     // Customers/$count => string
                                 } else {
                                     self::assert(false, 'Unexpected resource target kind');
                                 }
                             }
                         }
                     }
                 }
             }
         }
     }
     //Note: Response content type can be null for named stream
     if ($hasResponseBody && !is_null($responseContentType)) {
         if ($responseFormat != ResponseFormat::BINARY) {
             $responseContentType .= ';charset=utf-8';
         }
     }
     if ($hasResponseBody) {
         ResponseWriter::write($this, $requestDescription, $odataModelInstance, $responseContentType, $responseFormat);
     }
 }