image-rs / image

Encoding and decoding images in Rust
Apache License 2.0
4.93k stars 610 forks source link

Add serde support for image::ImageFormat #2254

Open Snapstromegon opened 4 months ago

Snapstromegon commented 4 months ago

I would like to be able to store the format of an image in a metadata database and send them between systems in a natively serialized way and not as strings.

My specific use case for this functionality is a photo system which automatically transforms images into multiple formats using a task queue which gets processed by another service. Each task contains the target size and format and for this I need to serialize the format so it can be send to the processing service. Right now this is possible by using a mime type string, but that makes the API not as nice to use and makes the API partly "stringly typed".

At the moment creating and reading a task looks something like this:

manager.push_task(Task {
  original_s3_path: source_path,
  target_s3_path: target_path,
  target_format_mime_type: format.to_mime_type(),
  target_max_size: Size::Width(1000),
});

// Sometime later

let task = manager.pop_task();
let format = ImageFormat::from_mime_type(task.target_format_mime_type);

Draft

(Optionally/feature gated) implementing serde::Deserialize and serde::Serialize on ImageFormat would allow to use serde on structs/enums that contain an ImageFormat. The implementation could use the mime type internally. Same could be useful for ColorType enums.

fintelia commented 4 months ago

I think we could derive Serialize/Deserialize for these types. Though, it would require placing the derive within a cfg_attr so it was only enabled when serde a serde feature was on.

The enums are marked non-exhaustive which I don't think matters, but I could be wrong?

Snapstromegon commented 4 months ago

I think something like this should work:

#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]

As far as I'm aware it doesn't matter if an enum is non-exhaustive.