thirdparty/google_appengine/google/appengine/api/images/__init__.py
changeset 3031 7678f72140e6
parent 2273 e4cb9c53db3e
equal deleted inserted replaced
3030:09cae668b536 3031:7678f72140e6
    83 
    83 
    84 class LargeImageError(Error):
    84 class LargeImageError(Error):
    85   """The image data given is too large to process."""
    85   """The image data given is too large to process."""
    86 
    86 
    87 
    87 
       
    88 class InvalidBlobKeyError(Error):
       
    89   """The provided blob key was invalid."""
       
    90 
       
    91 
    88 class Image(object):
    92 class Image(object):
    89   """Image object to manipulate."""
    93   """Image object to manipulate."""
    90 
    94 
    91   def __init__(self, image_data):
    95   def __init__(self, image_data=None, blob_key=None):
    92     """Constructor.
    96     """Constructor.
    93 
    97 
    94     Args:
    98     Args:
    95       image_data: str, image data in string form.
    99       image_data: str, image data in string form.
       
   100       blob_key: str, image data as a blobstore blob key.
    96 
   101 
    97     Raises:
   102     Raises:
    98       NotImageError if the given data is empty.
   103       NotImageError if the given data is empty.
    99     """
   104     """
   100     if not image_data:
   105     if not image_data and not blob_key:
   101       raise NotImageError("Empty image data.")
   106       raise NotImageError("Empty image data.")
       
   107     if image_data and blob_key:
       
   108       raise NotImageError("Can only take one image or blob key.")
   102 
   109 
   103     self._image_data = image_data
   110     self._image_data = image_data
       
   111     self._blob_key = blob_key
   104     self._transforms = []
   112     self._transforms = []
   105     self._width = None
   113     self._width = None
   106     self._height = None
   114     self._height = None
   107 
   115 
   108   def _check_transform_limits(self):
   116   def _check_transform_limits(self):
   121 
   129 
   122     Raises:
   130     Raises:
   123       NotImageError if the image data is not an image.
   131       NotImageError if the image data is not an image.
   124       BadImageError if the image data is corrupt.
   132       BadImageError if the image data is corrupt.
   125     """
   133     """
       
   134     if not self._image_data:
       
   135       raise NotImageError("Dimensions unavailable for blob key input")
   126     size = len(self._image_data)
   136     size = len(self._image_data)
   127     if size >= 6 and self._image_data.startswith("GIF"):
   137     if size >= 6 and self._image_data.startswith("GIF"):
   128       self._update_gif_dimensions()
   138       self._update_gif_dimensions()
   129     elif size >= 8 and self._image_data.startswith("\x89PNG\x0D\x0A\x1A\x0A"):
   139     elif size >= 8 and self._image_data.startswith("\x89PNG\x0D\x0A\x1A\x0A"):
   130       self._update_png_dimensions()
   140       self._update_png_dimensions()
   446     transform = images_service_pb.Transform()
   456     transform = images_service_pb.Transform()
   447     transform.set_autolevels(True)
   457     transform.set_autolevels(True)
   448 
   458 
   449     self._transforms.append(transform)
   459     self._transforms.append(transform)
   450 
   460 
       
   461   def _set_imagedata(self, imagedata):
       
   462     """Fills in an ImageData PB from this Image instance.
       
   463 
       
   464     Args:
       
   465       imagedata: An ImageData PB instance
       
   466     """
       
   467     if self._blob_key:
       
   468       imagedata.set_content("")
       
   469       imagedata.set_blob_key(self._blob_key)
       
   470     else:
       
   471       imagedata.set_content(self._image_data)
       
   472 
   451   def execute_transforms(self, output_encoding=PNG):
   473   def execute_transforms(self, output_encoding=PNG):
   452     """Perform transformations on given image.
   474     """Perform transformations on given image.
   453 
   475 
   454     Args:
   476     Args:
   455       output_encoding: A value from OUTPUT_ENCODING_TYPES.
   477       output_encoding: A value from OUTPUT_ENCODING_TYPES.
   461       BadRequestError when there is something wrong with the request
   483       BadRequestError when there is something wrong with the request
   462         specifications.
   484         specifications.
   463       NotImageError when the image data given is not an image.
   485       NotImageError when the image data given is not an image.
   464       BadImageError when the image data given is corrupt.
   486       BadImageError when the image data given is corrupt.
   465       LargeImageError when the image data given is too large to process.
   487       LargeImageError when the image data given is too large to process.
       
   488       InvalidBlobKeyError when the blob key provided is invalid.
   466       TransformtionError when something errors during image manipulation.
   489       TransformtionError when something errors during image manipulation.
   467       Error when something unknown, but bad, happens.
   490       Error when something unknown, but bad, happens.
   468     """
   491     """
   469     if output_encoding not in OUTPUT_ENCODING_TYPES:
   492     if output_encoding not in OUTPUT_ENCODING_TYPES:
   470       raise BadRequestError("Output encoding type not in recognized set "
   493       raise BadRequestError("Output encoding type not in recognized set "
   474       raise BadRequestError("Must specify at least one transformation.")
   497       raise BadRequestError("Must specify at least one transformation.")
   475 
   498 
   476     request = images_service_pb.ImagesTransformRequest()
   499     request = images_service_pb.ImagesTransformRequest()
   477     response = images_service_pb.ImagesTransformResponse()
   500     response = images_service_pb.ImagesTransformResponse()
   478 
   501 
   479     request.mutable_image().set_content(self._image_data)
   502     self._set_imagedata(request.mutable_image())
   480 
   503 
   481     for transform in self._transforms:
   504     for transform in self._transforms:
   482       request.add_transform().CopyFrom(transform)
   505       request.add_transform().CopyFrom(transform)
   483 
   506 
   484     request.mutable_output().set_mime_type(output_encoding)
   507     request.mutable_output().set_mime_type(output_encoding)
   500         raise BadImageError()
   523         raise BadImageError()
   501       elif (e.application_error ==
   524       elif (e.application_error ==
   502             images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   525             images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   503         raise LargeImageError()
   526         raise LargeImageError()
   504       elif (e.application_error ==
   527       elif (e.application_error ==
       
   528             images_service_pb.ImagesServiceError.INVALID_BLOB_KEY):
       
   529         raise InvalidBlobKeyError()
       
   530       elif (e.application_error ==
   505             images_service_pb.ImagesServiceError.UNSPECIFIED_ERROR):
   531             images_service_pb.ImagesServiceError.UNSPECIFIED_ERROR):
   506         raise TransformationError()
   532         raise TransformationError()
   507       else:
   533       else:
   508         raise Error()
   534         raise Error()
   509 
   535 
   510     self._image_data = response.image().content()
   536     self._image_data = response.image().content()
       
   537     self._blob_key = None
   511     self._transforms = []
   538     self._transforms = []
   512     self._width = None
   539     self._width = None
   513     self._height = None
   540     self._height = None
   514     return self._image_data
   541     return self._image_data
   515 
   542 
   543       Error when something unknown, but bad, happens.
   570       Error when something unknown, but bad, happens.
   544     """
   571     """
   545     request = images_service_pb.ImagesHistogramRequest()
   572     request = images_service_pb.ImagesHistogramRequest()
   546     response = images_service_pb.ImagesHistogramResponse()
   573     response = images_service_pb.ImagesHistogramResponse()
   547 
   574 
   548     request.mutable_image().set_content(self._image_data)
   575     self._set_imagedata(request.mutable_image())
       
   576 
   549     try:
   577     try:
   550       apiproxy_stub_map.MakeSyncCall("images",
   578       apiproxy_stub_map.MakeSyncCall("images",
   551                                      "Histogram",
   579                                      "Histogram",
   552                                      request,
   580                                      request,
   553                                      response)
   581                                      response)
   559             images_service_pb.ImagesServiceError.BAD_IMAGE_DATA):
   587             images_service_pb.ImagesServiceError.BAD_IMAGE_DATA):
   560         raise BadImageError()
   588         raise BadImageError()
   561       elif (e.application_error ==
   589       elif (e.application_error ==
   562             images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   590             images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   563         raise LargeImageError()
   591         raise LargeImageError()
       
   592       elif (e.application_error ==
       
   593             images_service_pb.ImagesServiceError.INVALID_BLOB_KEY):
       
   594         raise InvalidBlobKeyError()
   564       else:
   595       else:
   565         raise Error()
   596         raise Error()
   566     histogram = response.histogram()
   597     histogram = response.histogram()
   567     return [histogram.red_list(),
   598     return [histogram.red_list(),
   568             histogram.green_list(),
   599             histogram.green_list(),
   766     if anchor not in ANCHOR_TYPES:
   797     if anchor not in ANCHOR_TYPES:
   767       raise BadRequestError("Anchor type '%s' not in recognized set %s" %
   798       raise BadRequestError("Anchor type '%s' not in recognized set %s" %
   768                             (anchor, ANCHOR_TYPES))
   799                             (anchor, ANCHOR_TYPES))
   769     if image not in image_map:
   800     if image not in image_map:
   770       image_map[image] = request.image_size()
   801       image_map[image] = request.image_size()
   771       request.add_image().set_content(image)
   802 
       
   803       if isinstance(image, Image):
       
   804         image._set_imagedata(request.add_image())
       
   805       else:
       
   806         request.add_image().set_content(image)
   772 
   807 
   773     option = request.add_options()
   808     option = request.add_options()
   774     option.set_x_offset(x)
   809     option.set_x_offset(x)
   775     option.set_y_offset(y)
   810     option.set_y_offset(y)
   776     option.set_opacity(opacity)
   811     option.set_opacity(opacity)
   799       raise BadImageError()
   834       raise BadImageError()
   800     elif (e.application_error ==
   835     elif (e.application_error ==
   801           images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   836           images_service_pb.ImagesServiceError.IMAGE_TOO_LARGE):
   802       raise LargeImageError()
   837       raise LargeImageError()
   803     elif (e.application_error ==
   838     elif (e.application_error ==
       
   839           images_service_pb.ImagesServiceError.INVALID_BLOB_KEY):
       
   840       raise InvalidBlobKeyError()
       
   841     elif (e.application_error ==
   804           images_service_pb.ImagesServiceError.UNSPECIFIED_ERROR):
   842           images_service_pb.ImagesServiceError.UNSPECIFIED_ERROR):
   805       raise TransformationError()
   843       raise TransformationError()
   806     else:
   844     else:
   807       raise Error()
   845       raise Error()
   808 
   846