Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[RSDK-9660] - fix-camera-image-returning-no-mime-type #4674

Conversation

nicksanford
Copy link
Member

@nicksanford nicksanford commented Jan 3, 2025

https://viam.atlassian.net/browse/RSDK-9660

This fixes a bug in which the vision.CaptureAllFromCamera data collector receives an *rimage.LazyEncodedImage with a mime_type of empty string. This condition happens when a builtin vision service uses a remote or modular camera to get it's image. This causes those images to show up under the files tab in app.viam.com rather than the data tab when they are synced to the cloud.

  1. Change camera.DecodeImageFromCamera to always return a lazy image (for lower resource usage)
  2. Change camera.client.Image to return the mime_type of the camera.GetImageResponse when the camera.Image caller doesn't specify a mime_type. This is needed so that vision services (which frequently don't specify a mime_type in their call to camera.client.Image) to still be able to detect the mime_type of the image.
  3. Change camera.client.Image to no longer wrap the mime_type in the +lazy suffix, as the lazy suffix is a directive to the rimage package to wrap the image bytes in a lazy image, which is something which camera.client.Image should be deciding for all callers, especially given that the +lazy suffix will not be understood by mime_type libraries outside of viam. Point 1 makes it so that this isn't a breaking change for all RDK code.
  4. Change rimage.NewLazyEncodedImage to log a warning when the caller doesn't specify a mime_type and detect the mime type by sniffing the image's bytes.

@viambot viambot added the safe to test This pull request is marked safe to test from a trusted zone label Jan 3, 2025
Copy link
Contributor

github-actions bot commented Jan 3, 2025

Warning your change may break code samples. If your change modifies any of the following functions please contact @viamrobotics/fleet-management. Thanks!

component function
base IsMoving
board GPIOPinByName
camera Properties
encoder Properties
motor IsMoving
sensor Readings
servo Position
arm EndPosition
audio MediaProperties
gantry Lengths
gripper IsMoving
input_controller Controls
movement_sensor LinearAcceleration
power_sensor Power
pose_tracker Poses
motion GetPose
vision GetProperties

@viambot viambot added safe to test This pull request is marked safe to test from a trusted zone and removed safe to test This pull request is marked safe to test from a trusted zone labels Jan 3, 2025
}

return resp.Image, ImageMetadata{MimeType: utils.WithLazyMIMEType(resp.MimeType)}, nil
return resp.Image, ImageMetadata{MimeType: resp.MimeType}, nil
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm moving this utils.WithLazyMIMEType call here: https://github.com/viamrobotics/rdk/pull/4674/files#diff-4eab9b93978c09650defc23c4274a4c77d87cfdea7775d86dcf8c838ec207a01R170 as that is the only caller of Image in viam-server and the reason why we were adding the lazy mime type.

if resp.MimeType == "" {
// if the user expected a mime_type and the successful response didn't have a mime type, assume the
// response's mime_type was what the user requested
resp.MimeType = mimeType
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this makes it so that we only override the camera.GetImageResponse.MimeType if it is empty string and the caller specified an expected mime type.

@viambot viambot added safe to test This pull request is marked safe to test from a trusted zone and removed safe to test This pull request is marked safe to test from a trusted zone labels Jan 3, 2025
if mimeType == "" {
logging.Global().Warn("NewLazyEncodedImage called without a mime_type. " +
"Sniffing bytes to detect mime_type. Specify mime_type to reduce CPU utilization")
mimeType = http.DetectContentType(imgBytes)
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will attempt to detect the mime type of the image bytes if mimeType is empty.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a cool function from that library - nice to know it's in there.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It seems this method can return 3 mime types that would be interesting to us:

  • image/*
  • application/octet-stream
  • something else

It might be worth logging if this code path is getting application/octet-stream
Definitely worth logging if it's "something else"

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

great suggestion, done

test.That(t, mimeType, test.ShouldResemble, rutils.WithLazyMIMEType(rutils.MimeTypeJPEG))
resBytes, err := rimage.EncodeImage(ctx, imgPng, mimeType)
test.That(t, err, test.ShouldBeNil)
return resBytes, camera.ImageMetadata{MimeType: mimeType}, nil
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

change to non lazy

@nicksanford nicksanford force-pushed the fix-camera-image-returning-no-mime-type branch from 79e5393 to ed37538 Compare January 6, 2025 15:28
@viambot viambot added safe to test This pull request is marked safe to test from a trusted zone and removed safe to test This pull request is marked safe to test from a trusted zone labels Jan 6, 2025
@nicksanford nicksanford changed the title fix-camera-image-returning-no-mime-type [RSDK-9660] - fix-camera-image-returning-no-mime-type Jan 6, 2025
@nicksanford nicksanford marked this pull request as ready for review January 6, 2025 15:42
Copy link
Member

@randhid randhid left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

if mimeType == "" {
logging.Global().Warn("NewLazyEncodedImage called without a mime_type. " +
"Sniffing bytes to detect mime_type. Specify mime_type to reduce CPU utilization")
mimeType = http.DetectContentType(imgBytes)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a cool function from that library - nice to know it's in there.

Copy link
Member

@dgottlieb dgottlieb left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can't check the changes too closely for bugs -- I'm not well versed enough in this to spot something subtle.

Left a suggestion regarding the automatic detection. Doesn't change how applications would behave in the PR, just a diagnostic improvement.

if mimeType == "" {
logging.Global().Warn("NewLazyEncodedImage called without a mime_type. " +
"Sniffing bytes to detect mime_type. Specify mime_type to reduce CPU utilization")
mimeType = http.DetectContentType(imgBytes)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It seems this method can return 3 mime types that would be interesting to us:

  • image/*
  • application/octet-stream
  • something else

It might be worth logging if this code path is getting application/octet-stream
Definitely worth logging if it's "something else"

@viambot viambot added safe to test This pull request is marked safe to test from a trusted zone and removed safe to test This pull request is marked safe to test from a trusted zone labels Jan 6, 2025
@nicksanford nicksanford merged commit 7297934 into viamrobotics:main Jan 6, 2025
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
safe to test This pull request is marked safe to test from a trusted zone
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants