Fix to have deterministic order of commands (#5583)

This commit is contained in:
Jonathan Tran
2025-03-01 02:31:38 -05:00
committed by GitHub
parent 180d52280d
commit bbae9b6363
3 changed files with 23 additions and 10 deletions

View File

@ -5,6 +5,7 @@ use derive_docs::stdlib;
use kcmc::{each_cmd as mcmd, length_unit::LengthUnit, shared::CutType, ModelingCmd};
use kittycad_modeling_cmds as kcmc;
use super::utils::unique_count;
use crate::{
errors::{KclError, KclErrorDetails},
execution::{ChamferSurface, EdgeCut, ExecState, ExtrudeSurface, GeoMeta, KclValue, Solid},
@ -109,10 +110,8 @@ async fn inner_chamfer(
args: Args,
) -> Result<Box<Solid>, KclError> {
// Check if tags contains any duplicate values.
let mut tags = tags.clone();
tags.sort();
tags.dedup();
if tags.len() != tags.len() {
let unique_tags = unique_count(tags.clone());
if unique_tags != tags.len() {
return Err(KclError::Type(KclErrorDetails {
message: "Duplicate tags are not allowed.".to_string(),
source_ranges: vec![args.source_range],

View File

@ -11,6 +11,7 @@ use schemars::JsonSchema;
use serde::{Deserialize, Serialize};
use uuid::Uuid;
use super::utils::unique_count;
use crate::{
errors::{KclError, KclErrorDetails},
execution::{EdgeCut, ExecState, ExtrudeSurface, FilletSurface, GeoMeta, KclValue, Solid, TagIdentifier},
@ -20,7 +21,7 @@ use crate::{
};
/// A tag or a uuid of an edge.
#[derive(Debug, Clone, Deserialize, Serialize, PartialEq, ts_rs::TS, JsonSchema, Eq, Ord, PartialOrd, Hash)]
#[derive(Debug, Clone, Deserialize, Serialize, PartialEq, ts_rs::TS, JsonSchema, Eq, Hash)]
#[ts(export)]
#[serde(untagged)]
pub enum EdgeReference {
@ -129,10 +130,8 @@ async fn inner_fillet(
args: Args,
) -> Result<Box<Solid>, KclError> {
// Check if tags contains any duplicate values.
let mut unique_tags = tags.clone();
unique_tags.sort();
unique_tags.dedup();
if unique_tags.len() != tags.len() {
let unique_tags = unique_count(tags.clone());
if unique_tags != tags.len() {
return Err(KclError::Type(KclErrorDetails {
message: "Duplicate tags are not allowed.".to_string(),
source_ranges: vec![args.source_range],

View File

@ -1,4 +1,4 @@
use std::f64::consts::PI;
use std::{collections::HashSet, f64::consts::PI};
use kittycad_modeling_cmds::shared::Angle;
@ -8,6 +8,16 @@ use crate::{
source_range::SourceRange,
};
/// Count the number of unique items in a `Vec` in O(n) time.
pub(crate) fn unique_count<T: Eq + std::hash::Hash>(vec: Vec<T>) -> usize {
// Add to a set.
let mut set = HashSet::with_capacity(vec.len());
for item in vec {
set.insert(item);
}
set.len()
}
/// Get the distance between two points.
pub fn distance(a: Point2d, b: Point2d) -> f64 {
((b.x - a.x).powi(2) + (b.y - a.y).powi(2)).sqrt()
@ -676,6 +686,11 @@ mod get_tangential_arc_to_info_tests {
(num * 1000.0).round() / 1000.0
}
#[test]
fn test_unique_count() {
assert_eq!(unique_count(vec![1, 2, 2, 3, 2]), 3);
}
#[test]
fn test_basic_case() {
let result = get_tangential_arc_to_info(TangentialArcInfoInput {