Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 29 additions & 2 deletions plotly/src/plot.rs
Original file line number Diff line number Diff line change
Expand Up @@ -586,9 +586,9 @@ impl PartialEq for Plot {
mod tests {
use std::path::PathBuf;

#[cfg(feature = "kaleido")]
use base64::{engine::general_purpose, Engine as _};
use serde_json::{json, to_value};
#[cfg(not(target_os = "macos"))]
use {base64::engine::general_purpose, base64::Engine};

use super::*;
use crate::Scatter;
Expand Down Expand Up @@ -866,4 +866,31 @@ mod tests {
const LEN: usize = 10;
assert_eq!(expected[..LEN], image_svg[..LEN]);
}

#[cfg(target_os = "macos")]
#[test]
#[cfg(feature = "kaleido")]
fn save_surface_to_png() {
use crate::Surface;
let mut plot = Plot::new();
let z_matrix = vec![
vec![1.0, 2.0, 3.0],
vec![4.0, 5.0, 6.0],
vec![7.0, 8.0, 9.0],
];
let x_unique = vec![1.0, 2.0, 3.0];
let y_unique = vec![4.0, 5.0, 6.0];
let surface = Surface::new(z_matrix)
.x(x_unique)
.y(y_unique)
.name("Surface");

plot.add_trace(surface);
let dst = PathBuf::from("example.png");
plot.write_image("example.png", ImageFormat::PNG, 800, 600, 1.0);
assert!(dst.exists());
assert!(std::fs::remove_file(&dst).is_ok());
assert!(!dst.exists());
assert!(!plot.to_base64(ImageFormat::PNG, 1024, 680, 1.0).is_empty());
}
}
150 changes: 138 additions & 12 deletions plotly_kaleido/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -185,20 +185,34 @@ impl Kaleido {
) -> Result<String, Box<dyn std::error::Error>> {
let p = self.cmd_path.to_str().unwrap();

#[cfg(not(target_os = "macos"))]
let cmd_args = vec![
"plotly",
"--disable-gpu",
"--allow-file-access-from-files",
"--disable-breakpad",
"--disable-dev-shm-usage",
"--disable-software-rasterizer",
"--single-process",
"--no-sandbox",
];

// Add Kaleido issue #323
#[cfg(target_os = "macos")]
let cmd_args = vec![
"plotly",
"--allow-file-access-from-files",
"--disable-breakpad",
"--disable-dev-shm-usage",
"--disable-software-rasterizer",
"--single-process",
"--no-sandbox",
];

#[allow(clippy::zombie_processes)]
let mut process = Command::new(p)
.current_dir(self.cmd_path.parent().unwrap())
.args([
"plotly",
"--disable-gpu",
"--allow-file-access-from-files",
"--disable-breakpad",
"--disable-dev-shm-usage",
"--disable-software-rasterizer",
"--single-process",
"--disable-gpu",
"--no-sandbox",
])
.args(cmd_args)
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.stderr(Stdio::piped())
Expand All @@ -213,7 +227,6 @@ impl Kaleido {
.to_string()
)
});

{
let plot_data = PlotData::new(plotly_data, format, width, height, scale).to_json();
let mut process_stdin = process.stdin.take().unwrap();
Expand Down Expand Up @@ -287,6 +300,47 @@ mod tests {
.unwrap()
}

#[cfg(target_os = "macos")]
fn create_test_surface() -> Value {
to_value(json!({
"data": [
{
"name": "Surface",
"type": "surface",
"x": [
1.0,
2.0,
3.0
],
"y": [
4.0,
5.0,
6.0
],
"z": [
[
1.0,
2.0,
3.0
],
[
4.0,
5.0,
6.0
],
[
7.0,
8.0,
9.0
]
]
}
],
"layout": {}
}))
.unwrap()
}

#[test]
fn can_find_kaleido_executable() {
let _k = Kaleido::new();
Expand Down Expand Up @@ -378,4 +432,76 @@ mod tests {
assert!(r.is_ok());
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}

// Issue #241 workaround until https://github.com/plotly/Kaleido/issues/323 is resolved
#[cfg(target_os = "macos")]
#[test]
fn save_surface_png() {
let test_plot = create_test_surface();
let k = Kaleido::new();
let dst = PathBuf::from("example.png");
let r = k.save(dst.as_path(), &test_plot, "png", 1200, 900, 4.5);
assert!(r.is_ok());
assert!(dst.exists());
let metadata = std::fs::metadata(&dst).expect("Could not retrieve file metadata");
let file_size = metadata.len();
assert!(file_size > 0,);
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}
#[cfg(target_os = "macos")]
#[test]
fn save_surface_jpeg() {
let test_plot = create_test_surface();
let k = Kaleido::new();
let dst = PathBuf::from("example.jpeg");
let r = k.save(dst.as_path(), &test_plot, "jpeg", 1200, 900, 4.5);
assert!(r.is_ok());
assert!(dst.exists());
let metadata = std::fs::metadata(&dst).expect("Could not retrieve file metadata");
let file_size = metadata.len();
assert!(file_size > 0,);
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}
#[cfg(target_os = "macos")]
#[test]
fn save_surface_webp() {
let test_plot = create_test_surface();
let k = Kaleido::new();
let dst = PathBuf::from("example.webp");
let r = k.save(dst.as_path(), &test_plot, "webp", 1200, 900, 4.5);
assert!(r.is_ok());
assert!(dst.exists());
let metadata = std::fs::metadata(&dst).expect("Could not retrieve file metadata");
let file_size = metadata.len();
assert!(file_size > 0,);
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}
#[cfg(target_os = "macos")]
#[test]
fn save_surface_svg() {
let test_plot = create_test_surface();
let k = Kaleido::new();
let dst = PathBuf::from("example.svg");
let r = k.save(dst.as_path(), &test_plot, "svg", 1200, 900, 4.5);
assert!(r.is_ok());
assert!(dst.exists());
let metadata = std::fs::metadata(&dst).expect("Could not retrieve file metadata");
let file_size = metadata.len();
assert!(file_size > 0,);
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}
#[cfg(target_os = "macos")]
#[test]
fn save_surface_pdf() {
let test_plot = create_test_surface();
let k = Kaleido::new();
let dst = PathBuf::from("example.pdf");
let r = k.save(dst.as_path(), &test_plot, "pdf", 1200, 900, 4.5);
assert!(r.is_ok());
assert!(dst.exists());
let metadata = std::fs::metadata(&dst).expect("Could not retrieve file metadata");
let file_size = metadata.len();
assert!(file_size > 0,);
assert!(std::fs::remove_file(dst.as_path()).is_ok());
}
}
Loading