mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-26 18:21:59 +00:00
some fixes and lint cleanups
This commit is contained in:
@@ -22,9 +22,6 @@ import os
|
|||||||
import sys
|
import sys
|
||||||
|
|
||||||
bonsai_lib_path = os.environ.get("BONSAI_LIB_PATH")
|
bonsai_lib_path = os.environ.get("BONSAI_LIB_PATH")
|
||||||
print(os.environ)
|
|
||||||
print(bonsai_lib_path)
|
|
||||||
bonsai_version = os.environ.get("BONSAI_VERSION")
|
|
||||||
|
|
||||||
if bonsai_lib_path:
|
if bonsai_lib_path:
|
||||||
sys.path.insert(0, bonsai_lib_path)
|
sys.path.insert(0, bonsai_lib_path)
|
||||||
|
|||||||
@@ -2,7 +2,6 @@
|
|||||||
"wasm": {
|
"wasm": {
|
||||||
"wheel_url": "/worker/bin/ifcopenshell-0.8.3+bb329af-cp313-cp313-emscripten_4_0_9_wasm32.whl",
|
"wheel_url": "/worker/bin/ifcopenshell-0.8.3+bb329af-cp313-cp313-emscripten_4_0_9_wasm32.whl",
|
||||||
"odfpy_url": "/worker/bin/odfpy-1.4.2-py2.py3-none-any.whl",
|
"odfpy_url": "/worker/bin/odfpy-1.4.2-py2.py3-none-any.whl",
|
||||||
"api_py_url": "/worker/api.py",
|
"api_py_url": "/worker/api.py"
|
||||||
"pyodide_url": "https://cdn.jsdelivr.net/pyodide/v0.28.0/full/pyodide.js"
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -265,17 +265,17 @@ export async function deleteFacet(
|
|||||||
const spec = Module.documents[docId].specifications.specification[specId];
|
const spec = Module.documents[docId].specifications.specification[specId];
|
||||||
const list = (spec[clause] as Record<string, unknown> | undefined)?.[facet] as Facet[] | undefined;
|
const list = (spec[clause] as Record<string, unknown> | undefined)?.[facet] as Facet[] | undefined;
|
||||||
if (!list) return;
|
if (!list) return;
|
||||||
delete list[facetId];
|
list.splice(facetId, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getSpecUsage(spec?: Specification | null): IdsCardinality {
|
export function getSpecUsage(spec?: Specification | null): IdsCardinality {
|
||||||
if (!spec?.applicability) return 'required';
|
if (!spec?.applicability) return 'required';
|
||||||
const minOccurs = spec.applicability["@minOccurs"] as number | undefined;
|
const minOccurs = spec.applicability["@minOccurs"] as number | undefined;
|
||||||
const maxOccurs = spec.applicability["@maxOccurs"] as number | "unbounded" | undefined;
|
const maxOccurs = spec.applicability["@maxOccurs"] as number | "unbounded" | undefined;
|
||||||
|
|
||||||
if (minOccurs === 1 && maxOccurs === "unbounded") return 'required';
|
if (minOccurs !== 0) return 'required';
|
||||||
if (minOccurs === 0 && maxOccurs === "unbounded") return 'optional';
|
if (minOccurs === 0 && maxOccurs !== 0) return 'optional';
|
||||||
if (minOccurs === 0 && maxOccurs === 0) return 'prohibited';
|
if (maxOccurs === 0) return 'prohibited';
|
||||||
return 'required';
|
return 'required';
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -34,7 +34,7 @@
|
|||||||
(facet as Record<string, unknown>)[prop] = value;
|
(facet as Record<string, unknown>)[prop] = value;
|
||||||
};
|
};
|
||||||
|
|
||||||
const baseId = `facet-${facetType}-${index}`;
|
let baseId = $derived(`facet-${facetType}-${index}`);
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="restriction-item">
|
<div class="restriction-item">
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
import { error, success } from "$src/modules/utils/toast.svelte";
|
import { error, success } from "$src/modules/utils/toast.svelte";
|
||||||
import * as Tooltip from "$src/lib/components/ui/tooltip";
|
import * as Tooltip from "$src/lib/components/ui/tooltip";
|
||||||
import type { AuditReport, AuditReportData } from "$src/types/report";
|
import type { AuditReport, AuditReportData } from "$src/types/report";
|
||||||
import type { DocumentState, IdsDocument } from "$src/types/ids";
|
import type { DocumentState, IdsDocument, Specification } from "$src/types/ids";
|
||||||
|
|
||||||
let activeDocument = $derived(
|
let activeDocument = $derived(
|
||||||
IDS.Module.activeDocument ? (IDS.Module.documents[IDS.Module.activeDocument] as IdsDocument) : null
|
IDS.Module.activeDocument ? (IDS.Module.documents[IDS.Module.activeDocument] as IdsDocument) : null
|
||||||
@@ -19,6 +19,8 @@
|
|||||||
let expandedRequirements = $state(new Set<string>());
|
let expandedRequirements = $state(new Set<string>());
|
||||||
let allExpanded = $state(false);
|
let allExpanded = $state(false);
|
||||||
|
|
||||||
|
type SpecificationStatus = boolean | 'skipped' | null;
|
||||||
|
|
||||||
// Open Editor mode and jump to a specific specification
|
// Open Editor mode and jump to a specific specification
|
||||||
function editSpecification(index: number) {
|
function editSpecification(index: number) {
|
||||||
if (IDS.Module.activeDocument) {
|
if (IDS.Module.activeDocument) {
|
||||||
@@ -55,7 +57,7 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function getSpecificationStatus(specIndex: number, auditData: AuditReportData) {
|
function getSpecificationStatus(specIndex: number, auditData: AuditReportData): SpecificationStatus {
|
||||||
const spec = auditData.specifications[specIndex];
|
const spec = auditData.specifications[specIndex];
|
||||||
if (!spec) return null;
|
if (!spec) return null;
|
||||||
return spec.is_skipped ? 'skipped' : spec.status;
|
return spec.is_skipped ? 'skipped' : spec.status;
|
||||||
@@ -98,6 +100,10 @@
|
|||||||
return null; // No reason needed for passed specifications
|
return null; // No reason needed for passed specifications
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function getDocumentSpecificationUsage(spec: Specification) {
|
||||||
|
return IDS.getSpecUsage(spec);
|
||||||
|
}
|
||||||
|
|
||||||
async function handleDownloadReport() {
|
async function handleDownloadReport() {
|
||||||
if (!auditReport) return;
|
if (!auditReport) return;
|
||||||
|
|
||||||
@@ -223,6 +229,7 @@
|
|||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
{#each activeDocument.specifications.specification as spec, index}
|
{#each activeDocument.specifications.specification as spec, index}
|
||||||
|
{@const usage = getDocumentSpecificationUsage(spec)}
|
||||||
<div class="specification-card {auditReport ? 'with-audit' : ''} {auditReport && getSpecificationStatus(index, auditReport.data) !== null ? (getSpecificationStatus(index, auditReport.data) === 'skipped' ? 'spec-skipped' : (getSpecificationStatus(index, auditReport.data) ? 'spec-pass' : 'spec-fail')) : ''}">
|
<div class="specification-card {auditReport ? 'with-audit' : ''} {auditReport && getSpecificationStatus(index, auditReport.data) !== null ? (getSpecificationStatus(index, auditReport.data) === 'skipped' ? 'spec-skipped' : (getSpecificationStatus(index, auditReport.data) ? 'spec-pass' : 'spec-fail')) : ''}">
|
||||||
<div
|
<div
|
||||||
class="spec-card-header"
|
class="spec-card-header"
|
||||||
@@ -260,19 +267,19 @@
|
|||||||
<p class="spec-description">{spec["@description"]}</p>
|
<p class="spec-description">{spec["@description"]}</p>
|
||||||
{/if}
|
{/if}
|
||||||
<div class="spec-stats">
|
<div class="spec-stats">
|
||||||
{#if spec.applicability["@minOccurs"] === 1 && spec.applicability["@maxOccurs"] === 'unbounded'}
|
{#if usage === 'required'}
|
||||||
<span class="stat-item">Required</span>
|
<span class="stat-item">Required</span>
|
||||||
{/if}
|
{/if}
|
||||||
{#if spec.applicability["@minOccurs"] === 0 && spec.applicability["@maxOccurs"] === 'unbounded'}
|
{#if usage === 'optional'}
|
||||||
<span class="stat-item">Optional</span>
|
<span class="stat-item">Optional</span>
|
||||||
{/if}
|
{/if}
|
||||||
{#if spec.applicability["@minOccurs"] === 0 && spec.applicability["@maxOccurs"] === 0}
|
{#if usage === 'prohibited'}
|
||||||
<span class="stat-item">Prohibited</span>
|
<span class="stat-item">Prohibited</span>
|
||||||
{/if}
|
{/if}
|
||||||
{#if auditReport}
|
{#if auditReport}
|
||||||
{@const stats = getSpecificationStats(index, auditReport.data)}
|
{@const stats = getSpecificationStats(index, auditReport.data)}
|
||||||
{@const status = getSpecificationStatus(index, auditReport.data)}
|
{@const status = getSpecificationStatus(index, auditReport.data)}
|
||||||
{#if stats && spec.applicability["@maxOccurs"] !== 0 && status !== 'skipped'}
|
{#if stats && usage !== 'prohibited' && status !== 'skipped'}
|
||||||
<span class="stat-item">Checks: {stats.checksPassed}/{stats.checksTotal}</span>
|
<span class="stat-item">Checks: {stats.checksPassed}/{stats.checksTotal}</span>
|
||||||
<span class="stat-item">Requirements: {stats.requirementsPassed}/{stats.requirements}</span>
|
<span class="stat-item">Requirements: {stats.requirementsPassed}/{stats.requirements}</span>
|
||||||
{/if}
|
{/if}
|
||||||
@@ -325,12 +332,13 @@
|
|||||||
|
|
||||||
{#if auditReport}
|
{#if auditReport}
|
||||||
{@const status = getSpecificationStatus(index, auditReport.data)}
|
{@const status = getSpecificationStatus(index, auditReport.data)}
|
||||||
{#if ! status && spec.applicability["@maxOccurs"] == 0}
|
{#if status === false && usage === 'prohibited'}
|
||||||
{@const specReport = auditReport.data.specifications[index]}
|
{@const specReport = auditReport.data.specifications[index]}
|
||||||
|
{@const applicableEntities = specReport.applicable_entities ?? []}
|
||||||
<div class="entity-tables">
|
<div class="entity-tables">
|
||||||
{#if specReport.applicable_entities && specReport.applicable_entities.length > 0}
|
{#if applicableEntities.length > 0}
|
||||||
<div class="entity-table-section fail">
|
<div class="entity-table-section fail">
|
||||||
<h4>Failed Elements ({specReport.applicable_entities.length})</h4>
|
<h4>Failed Elements ({applicableEntities.length})</h4>
|
||||||
<div class="entity-table-container">
|
<div class="entity-table-container">
|
||||||
<Tooltip.Provider>
|
<Tooltip.Provider>
|
||||||
<table class="entity-table">
|
<table class="entity-table">
|
||||||
@@ -346,7 +354,7 @@
|
|||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
{#each specReport.applicable_entities.slice(0, 10) as entity}
|
{#each applicableEntities.slice(0, 10) as entity}
|
||||||
<tr>
|
<tr>
|
||||||
<td>{entity.class}</td>
|
<td>{entity.class}</td>
|
||||||
<td>{entity.predefined_type || '-'}</td>
|
<td>{entity.predefined_type || '-'}</td>
|
||||||
@@ -402,9 +410,9 @@
|
|||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
{/each}
|
{/each}
|
||||||
{#if specReport.applicable_entities.length > 10}
|
{#if applicableEntities.length > 10}
|
||||||
<tr class="more-row">
|
<tr class="more-row">
|
||||||
<td colspan="7">... {specReport.applicable_entities.length - 10} more failing elements not shown ...</td>
|
<td colspan="7">... {applicableEntities.length - 10} more failing elements not shown ...</td>
|
||||||
</tr>
|
</tr>
|
||||||
{/if}
|
{/if}
|
||||||
</tbody>
|
</tbody>
|
||||||
|
|||||||
@@ -1,6 +1,14 @@
|
|||||||
<script lang="ts">
|
<script lang="ts">
|
||||||
import Svelecte from 'svelecte';
|
import Svelecte from 'svelecte';
|
||||||
import { getEntityClasses, getMaterialCategories, getClassificationSystems, getDataTypes, getPredefinedTypes, getEntityAttributes, getApplicablePsets } from '$src/modules/api/api.svelte';
|
import {
|
||||||
|
getApplicablePsets,
|
||||||
|
getClassificationSystems,
|
||||||
|
getDataTypes,
|
||||||
|
getEntityAttributes,
|
||||||
|
getEntityClasses,
|
||||||
|
getMaterialCategories,
|
||||||
|
getPredefinedTypes
|
||||||
|
} from '$src/modules/api/api.svelte';
|
||||||
import * as IDS from '$src/modules/api/ids.svelte';
|
import * as IDS from '$src/modules/api/ids.svelte';
|
||||||
import type { DocumentState, Facet, FacetValue, IdsDocument, Restriction, RestrictionValue, Specification } from '$src/types/ids';
|
import type { DocumentState, Facet, FacetValue, IdsDocument, Restriction, RestrictionValue, Specification } from '$src/types/ids';
|
||||||
|
|
||||||
@@ -29,16 +37,17 @@
|
|||||||
autocomplete?: AutocompleteType;
|
autocomplete?: AutocompleteType;
|
||||||
isSpecialProp?: boolean;
|
isSpecialProp?: boolean;
|
||||||
} = $props();
|
} = $props();
|
||||||
|
|
||||||
const isEntityNameField = autocomplete === 'entityName';
|
|
||||||
const isMaterialField = autocomplete === 'material';
|
|
||||||
const isClassificationSystemField = autocomplete === 'classificationSystem';
|
|
||||||
const isPredefinedTypeField = autocomplete === 'predefinedType';
|
|
||||||
const isAttributeNameField = autocomplete === 'attributeName';
|
|
||||||
const isPropertySetField = autocomplete === 'propertySet';
|
|
||||||
const isDataTypeField = autocomplete === 'dataType';
|
|
||||||
|
|
||||||
const baseId = `restriction-${fieldName}-${Math.random().toString(36).slice(2, 8)}`;
|
let isEntityNameField = $derived(autocomplete === 'entityName');
|
||||||
|
let isMaterialField = $derived(autocomplete === 'material');
|
||||||
|
let isClassificationSystemField = $derived(autocomplete === 'classificationSystem');
|
||||||
|
let isPredefinedTypeField = $derived(autocomplete === 'predefinedType');
|
||||||
|
let isAttributeNameField = $derived(autocomplete === 'attributeName');
|
||||||
|
let isPropertySetField = $derived(autocomplete === 'propertySet');
|
||||||
|
let isDataTypeField = $derived(autocomplete === 'dataType');
|
||||||
|
|
||||||
|
const uniqueId = Math.random().toString(36).slice(2, 8);
|
||||||
|
let baseId = $derived(`restriction-${fieldName}-${uniqueId}`);
|
||||||
|
|
||||||
// Predefined Types autocompletions
|
// Predefined Types autocompletions
|
||||||
let predefinedTypeOptions: string[] = $state([]);
|
let predefinedTypeOptions: string[] = $state([]);
|
||||||
|
|||||||
@@ -26,6 +26,11 @@
|
|||||||
? (activeDocument.specifications.specification[documentState.activeSpecification] as Specification)
|
? (activeDocument.specifications.specification[documentState.activeSpecification] as Specification)
|
||||||
: null
|
: null
|
||||||
);
|
);
|
||||||
|
let importableDocuments = $derived(
|
||||||
|
Object.entries(IDS.Module.documents).filter(
|
||||||
|
([docId, doc]) => docId !== IDS.Module.activeDocument && doc.specifications?.specification?.length > 0
|
||||||
|
) as [string, IdsDocument][]
|
||||||
|
);
|
||||||
|
|
||||||
async function addNewSpecification() {
|
async function addNewSpecification() {
|
||||||
if (!IDS.Module.activeDocument) return;
|
if (!IDS.Module.activeDocument) return;
|
||||||
@@ -153,8 +158,7 @@
|
|||||||
Import from IDS
|
Import from IDS
|
||||||
</DropdownMenu.SubTrigger>
|
</DropdownMenu.SubTrigger>
|
||||||
<DropdownMenu.SubContent class="w-64 max-h-64 overflow-y-auto">
|
<DropdownMenu.SubContent class="w-64 max-h-64 overflow-y-auto">
|
||||||
{#each Object.entries(IDS.Module.documents) as [docId, doc]}
|
{#each importableDocuments as [docId, doc], docIndex}
|
||||||
{#if docId !== IDS.Module.activeDocument && doc.specifications?.specification?.length > 0}
|
|
||||||
<DropdownMenu.Label class="font-medium text-xs text-muted-foreground px-2 py-1 truncate">
|
<DropdownMenu.Label class="font-medium text-xs text-muted-foreground px-2 py-1 truncate">
|
||||||
{doc.info?.title || 'Untitled Document'}
|
{doc.info?.title || 'Untitled Document'}
|
||||||
</DropdownMenu.Label>
|
</DropdownMenu.Label>
|
||||||
@@ -169,12 +173,11 @@
|
|||||||
</span>
|
</span>
|
||||||
</DropdownMenu.Item>
|
</DropdownMenu.Item>
|
||||||
{/each}
|
{/each}
|
||||||
{#if Object.entries(IDS.Module.documents).filter(([id, d]) => id !== IDS.Module.activeDocument && d.specifications?.specification?.length > 0).indexOf([docId, doc]) < Object.entries(IDS.Module.documents).filter(([id, d]) => id !== IDS.Module.activeDocument && d.specifications?.specification?.length > 0).length - 1}
|
{#if docIndex < importableDocuments.length - 1}
|
||||||
<DropdownMenu.Separator />
|
<DropdownMenu.Separator />
|
||||||
{/if}
|
{/if}
|
||||||
{/if}
|
|
||||||
{/each}
|
{/each}
|
||||||
{#if Object.entries(IDS.Module.documents).filter(([docId, doc]) => docId !== IDS.Module.activeDocument && doc.specifications?.specification?.length > 0).length === 0}
|
{#if importableDocuments.length === 0}
|
||||||
<DropdownMenu.Item disabled>
|
<DropdownMenu.Item disabled>
|
||||||
<span class="text-sm">No specifications available to import</span>
|
<span class="text-sm">No specifications available to import</span>
|
||||||
</DropdownMenu.Item>
|
</DropdownMenu.Item>
|
||||||
|
|||||||
@@ -44,6 +44,7 @@ export type AuditSpecification = {
|
|||||||
description: string;
|
description: string;
|
||||||
instructions: string;
|
instructions: string;
|
||||||
status: boolean;
|
status: boolean;
|
||||||
|
is_skipped?: boolean;
|
||||||
is_ifc_version: boolean;
|
is_ifc_version: boolean;
|
||||||
total_applicable: number;
|
total_applicable: number;
|
||||||
total_applicable_pass: number;
|
total_applicable_pass: number;
|
||||||
@@ -55,6 +56,7 @@ export type AuditSpecification = {
|
|||||||
percent_checks_pass: ResultsPercent;
|
percent_checks_pass: ResultsPercent;
|
||||||
cardinality: string;
|
cardinality: string;
|
||||||
applicability: string[];
|
applicability: string[];
|
||||||
|
applicable_entities?: AuditReportEntity[];
|
||||||
requirements: AuditRequirement[];
|
requirements: AuditRequirement[];
|
||||||
total_requirements?: number;
|
total_requirements?: number;
|
||||||
total_requirements_pass?: number;
|
total_requirements_pass?: number;
|
||||||
|
|||||||
Reference in New Issue
Block a user