#986: confine Blender exports and trim generated header

This commit is contained in:
Krueels
2026-10-29 20:15:25 -03:00
parent e2b56f1ba5
commit 73817dc3f0
3 changed files with 29 additions and 2 deletions
+1
View File
@@ -97,6 +97,7 @@ const MIXED_WRITES: &[(&str, &[&str])] = &[("templates.create", &["projectPath",
/// Commands that write files named by these parameters.
const WRITES: &[(&str, &[&str])] = &[
("camera.exportBlender", &["path"]),
("file.save", &["path"]),
("file.saveAs", &["path"]),
("file.saveCopy", &["path"]),
+27
View File
@@ -1473,3 +1473,30 @@ fn automation_roots_refuse_running_script_code() {
call_json(&mut s, "execute_command", json!({"command": "scriptui.list"}));
let _ = std::fs::remove_dir_all(&base);
}
#[test]
fn blender_export_requires_an_absolute_path_in_a_write_root() {
use crate::confine::Confinement;
let base = std::env::temp_dir().join(format!("ec-blender-confine-{}", std::process::id()));
let (read, write) = (base.join("read"), base.join("write"));
for dir in [&read, &write] {
std::fs::create_dir_all(dir).unwrap();
}
let confinement = Confinement::new(std::slice::from_ref(&read), std::slice::from_ref(&write)).unwrap();
let check = |path: &std::path::Path| confinement.check_command("camera.exportBlender", &json!({"path": path}));
assert_eq!(check(&write.join("scene.py")).unwrap(), None);
for path in [read.join("scene.py"), base.join("outside.py"), write.join("../read/scene.py")] {
assert!(check(&path).is_err(), "must deny {}", path.display());
}
for path in ["scene.py", "./scene.py", "write/scene.py", "../scene.py"] {
let error = check(std::path::Path::new(path)).unwrap_err().to_string();
assert!(error.contains("give an absolute path"), "{path}: {error}");
}
let read_only = Confinement::new(std::slice::from_ref(&write), &[]).unwrap();
assert!(read_only.check_command("camera.exportBlender", &json!({"path": write.join("scene.py")})).is_err());
for path in [json!(read.join("scene.py")), json!("scene.py"), json!("$1.path")] {
let batch = json!({"steps": [{"command": "camera.exportBlender", "params": {"path": path}}]});
assert!(confinement.check_command("engine.batch", &batch).is_err());
}
std::fs::remove_dir_all(&base).unwrap();
}
+1 -2
View File
@@ -2,8 +2,7 @@
# Run in Blender's Scripting workspace (Open, Run Script), or:
# blender --background --python "Tracked Scene.py"
# Creates a NEW scene; existing scenes and objects are preserved. Save the .blend yourself.
# Public API references: https://docs.blender.org/api/4.5/bpy.types.Camera.html
# https://docs.blender.org/api/4.5/bpy.types.ImageUser.html
# Public API types: bpy.types.Camera, bpy.types.ImageUser
import json
import math
import os