diff --git a/drizzle/migrations/0001_rainy_rictor.sql b/drizzle/migrations/0001_rainy_rictor.sql new file mode 100644 index 0000000..d253035 --- /dev/null +++ b/drizzle/migrations/0001_rainy_rictor.sql @@ -0,0 +1 @@ +ALTER TABLE "parts" ADD COLUMN "value_numeric" double precision; \ No newline at end of file diff --git a/drizzle/migrations/meta/0001_snapshot.json b/drizzle/migrations/meta/0001_snapshot.json new file mode 100644 index 0000000..dd48cee --- /dev/null +++ b/drizzle/migrations/meta/0001_snapshot.json @@ -0,0 +1,2409 @@ +{ + "id": "ab78a3f2-a0c7-41ad-a5c8-925177d7862f", + "prevId": "cebee925-8ad2-4acf-8d4d-7dfe0e514aa6", + "version": "7", + "dialect": "postgresql", + "tables": { + "public.checklist_items": { + "name": "checklist_items", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "checklist_id": { + "name": "checklist_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "text": { + "name": "text", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "item_type": { + "name": "item_type", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'checkbox'" + }, + "unit": { + "name": "unit", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "checked": { + "name": "checked", + "type": "boolean", + "primaryKey": false, + "notNull": true, + "default": false + }, + "value": { + "name": "value", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "sort_order": { + "name": "sort_order", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 0 + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "checklist_items_checklist_idx": { + "name": "checklist_items_checklist_idx", + "columns": [ + { + "expression": "checklist_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "checklist_items_checklist_id_device_checklists_id_fk": { + "name": "checklist_items_checklist_id_device_checklists_id_fk", + "tableFrom": "checklist_items", + "tableTo": "device_checklists", + "columnsFrom": [ + "checklist_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.checklist_templates": { + "name": "checklist_templates", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": {}, + "foreignKeys": {}, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.component_documents": { + "name": "component_documents", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "component_id": { + "name": "component_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "file_path": { + "name": "file_path", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "original_filename": { + "name": "original_filename", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "file_type": { + "name": "file_type", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "uploaded_at": { + "name": "uploaded_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "component_documents_component_idx": { + "name": "component_documents_component_idx", + "columns": [ + { + "expression": "component_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "component_documents_component_id_components_id_fk": { + "name": "component_documents_component_id_components_id_fk", + "tableFrom": "component_documents", + "tableTo": "components", + "columnsFrom": [ + "component_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.component_images": { + "name": "component_images", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "component_id": { + "name": "component_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "file_path": { + "name": "file_path", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "thumbnail_path": { + "name": "thumbnail_path", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "caption": { + "name": "caption", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "uploaded_at": { + "name": "uploaded_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "component_images_component_idx": { + "name": "component_images_component_idx", + "columns": [ + { + "expression": "component_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "component_images_component_id_components_id_fk": { + "name": "component_images_component_id_components_id_fk", + "tableFrom": "component_images", + "tableTo": "components", + "columnsFrom": [ + "component_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.component_instances": { + "name": "component_instances", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "component_id": { + "name": "component_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "instance_number": { + "name": "instance_number", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 1 + }, + "serial_number": { + "name": "serial_number", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "condition": { + "name": "condition", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'Working'" + }, + "firmware_version": { + "name": "firmware_version", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "notes": { + "name": "notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "current_device_id": { + "name": "current_device_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "location_id": { + "name": "location_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "instances_component_idx": { + "name": "instances_component_idx", + "columns": [ + { + "expression": "component_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "instances_device_idx": { + "name": "instances_device_idx", + "columns": [ + { + "expression": "current_device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "instances_location_idx": { + "name": "instances_location_idx", + "columns": [ + { + "expression": "location_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "component_instances_component_id_components_id_fk": { + "name": "component_instances_component_id_components_id_fk", + "tableFrom": "component_instances", + "tableTo": "components", + "columnsFrom": [ + "component_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + }, + "component_instances_current_device_id_devices_id_fk": { + "name": "component_instances_current_device_id_devices_id_fk", + "tableFrom": "component_instances", + "tableTo": "devices", + "columnsFrom": [ + "current_device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "set null", + "onUpdate": "no action" + }, + "component_instances_location_id_locations_id_fk": { + "name": "component_instances_location_id_locations_id_fk", + "tableFrom": "component_instances", + "tableTo": "locations", + "columnsFrom": [ + "location_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "no action", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": { + "instances_condition_check": { + "name": "instances_condition_check", + "value": "\"component_instances\".\"condition\" IN ('Working', 'Faulty', 'Unknown', 'Refurbished')" + } + }, + "isRLSEnabled": false + }, + "public.components": { + "name": "components", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "component_type": { + "name": "component_type", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "brand": { + "name": "brand", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "part_number": { + "name": "part_number", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "specs": { + "name": "specs", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "notes": { + "name": "notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "default_condition": { + "name": "default_condition", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'Working'" + }, + "default_firmware_version": { + "name": "default_firmware_version", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "default_location_id": { + "name": "default_location_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "disabled": { + "name": "disabled", + "type": "boolean", + "primaryKey": false, + "notNull": true, + "default": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "components_type_idx": { + "name": "components_type_idx", + "columns": [ + { + "expression": "component_type", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "components_default_location_id_locations_id_fk": { + "name": "components_default_location_id_locations_id_fk", + "tableFrom": "components", + "tableTo": "locations", + "columnsFrom": [ + "default_location_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "no action", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.computer_details": { + "name": "computer_details", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "os_version": { + "name": "os_version", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "firmware_version": { + "name": "firmware_version", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "installed_software": { + "name": "installed_software", + "type": "text", + "primaryKey": false, + "notNull": false + } + }, + "indexes": {}, + "foreignKeys": { + "computer_details_device_id_devices_id_fk": { + "name": "computer_details_device_id_devices_id_fk", + "tableFrom": "computer_details", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": { + "computer_details_device_id_unique": { + "name": "computer_details_device_id_unique", + "nullsNotDistinct": false, + "columns": [ + "device_id" + ] + } + }, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.device_checklists": { + "name": "device_checklists", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "device_checklists_device_idx": { + "name": "device_checklists_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "device_checklists_device_id_devices_id_fk": { + "name": "device_checklists_device_id_devices_id_fk", + "tableFrom": "device_checklists", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.device_documents": { + "name": "device_documents", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "file_path": { + "name": "file_path", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "original_filename": { + "name": "original_filename", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "file_type": { + "name": "file_type", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "uploaded_at": { + "name": "uploaded_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "device_documents_device_idx": { + "name": "device_documents_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "device_documents_device_id_devices_id_fk": { + "name": "device_documents_device_id_devices_id_fk", + "tableFrom": "device_documents", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.device_images": { + "name": "device_images", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "file_path": { + "name": "file_path", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "thumbnail_path": { + "name": "thumbnail_path", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "caption": { + "name": "caption", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "sort_order": { + "name": "sort_order", + "type": "integer", + "primaryKey": false, + "notNull": false, + "default": 0 + }, + "uploaded_at": { + "name": "uploaded_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "device_images_device_idx": { + "name": "device_images_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "device_images_device_id_devices_id_fk": { + "name": "device_images_device_id_devices_id_fk", + "tableFrom": "device_images", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.device_log": { + "name": "device_log", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "type": { + "name": "type", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "condition_after": { + "name": "condition_after", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "performed_by": { + "name": "performed_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "performed_at": { + "name": "performed_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "device_log_device_idx": { + "name": "device_log_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "device_log_date_idx": { + "name": "device_log_date_idx", + "columns": [ + { + "expression": "performed_at", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "device_log_device_id_devices_id_fk": { + "name": "device_log_device_id_devices_id_fk", + "tableFrom": "device_log", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": { + "device_log_type_check": { + "name": "device_log_type_check", + "value": "\"device_log\".\"type\" IN ('repair', 'inspection', 'cleaning', 'modification', 'diagnostic', 'recap', 'other')" + } + }, + "isRLSEnabled": false + }, + "public.device_tags": { + "name": "device_tags", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "tag_uid": { + "name": "tag_uid", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "payload_url": { + "name": "payload_url", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "written_by": { + "name": "written_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "written_at": { + "name": "written_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "device_tags_device_idx": { + "name": "device_tags_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "device_tags_written_at_idx": { + "name": "device_tags_written_at_idx", + "columns": [ + { + "expression": "written_at", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "device_tags_device_id_devices_id_fk": { + "name": "device_tags_device_id_devices_id_fk", + "tableFrom": "device_tags", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.devices": { + "name": "devices", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "category": { + "name": "category", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "brand": { + "name": "brand", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "model": { + "name": "model", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "serial_number": { + "name": "serial_number", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "year": { + "name": "year", + "type": "integer", + "primaryKey": false, + "notNull": false + }, + "condition": { + "name": "condition", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'Waiting to be Tested'" + }, + "voltage": { + "name": "voltage", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "frequency": { + "name": "frequency", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "origin": { + "name": "origin", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "fault_description": { + "name": "fault_description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "repair_notes": { + "name": "repair_notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "location_id": { + "name": "location_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "initial_condition": { + "name": "initial_condition", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "general_notes": { + "name": "general_notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "disabled": { + "name": "disabled", + "type": "boolean", + "primaryKey": false, + "notNull": true, + "default": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "devices_category_idx": { + "name": "devices_category_idx", + "columns": [ + { + "expression": "category", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "devices_condition_idx": { + "name": "devices_condition_idx", + "columns": [ + { + "expression": "condition", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "devices_location_idx": { + "name": "devices_location_idx", + "columns": [ + { + "expression": "location_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "devices_location_id_locations_id_fk": { + "name": "devices_location_id_locations_id_fk", + "tableFrom": "devices", + "tableTo": "locations", + "columnsFrom": [ + "location_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "no action", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": { + "devices_category_check": { + "name": "devices_category_check", + "value": "\"devices\".\"category\" IN ('Computer', 'Audio Equipment', 'Peripheral', 'Other')" + }, + "devices_condition_check": { + "name": "devices_condition_check", + "value": "\"devices\".\"condition\" IN ('Working', 'In Repair', 'Waiting for Repair', 'Waiting to be Tested', 'Unrepairable')" + } + }, + "isRLSEnabled": false + }, + "public.feature_requests": { + "name": "feature_requests", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "status": { + "name": "status", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'open'" + }, + "votes": { + "name": "votes", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 0 + }, + "created_by": { + "name": "created_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": {}, + "foreignKeys": {}, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.installation_log": { + "name": "installation_log", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "instance_id": { + "name": "instance_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "action": { + "name": "action", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "performed_by": { + "name": "performed_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "notes": { + "name": "notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "performed_at": { + "name": "performed_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "install_log_instance_idx": { + "name": "install_log_instance_idx", + "columns": [ + { + "expression": "instance_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "install_log_device_idx": { + "name": "install_log_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "install_log_date_idx": { + "name": "install_log_date_idx", + "columns": [ + { + "expression": "performed_at", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "installation_log_instance_id_component_instances_id_fk": { + "name": "installation_log_instance_id_component_instances_id_fk", + "tableFrom": "installation_log", + "tableTo": "component_instances", + "columnsFrom": [ + "instance_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + }, + "installation_log_device_id_devices_id_fk": { + "name": "installation_log_device_id_devices_id_fk", + "tableFrom": "installation_log", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": { + "install_log_action_check": { + "name": "install_log_action_check", + "value": "\"installation_log\".\"action\" IN ('installed', 'removed', 'swapped')" + } + }, + "isRLSEnabled": false + }, + "public.locations": { + "name": "locations", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "name": { + "name": "name", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "parent_id": { + "name": "parent_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": {}, + "foreignKeys": { + "locations_parent_id_locations_id_fk": { + "name": "locations_parent_id_locations_id_fk", + "tableFrom": "locations", + "tableTo": "locations", + "columnsFrom": [ + "parent_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "no action", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.parts": { + "name": "parts", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "name": { + "name": "name", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "category": { + "name": "category", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "mpn": { + "name": "mpn", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "value": { + "name": "value", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "value_numeric": { + "name": "value_numeric", + "type": "double precision", + "primaryKey": false, + "notNull": false + }, + "voltage": { + "name": "voltage", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "tolerance": { + "name": "tolerance", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "power": { + "name": "power", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "mounting": { + "name": "mounting", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "package": { + "name": "package", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "quantity": { + "name": "quantity", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 0 + }, + "unit": { + "name": "unit", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'pcs'" + }, + "location_id": { + "name": "location_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "notes": { + "name": "notes", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "parts_category_idx": { + "name": "parts_category_idx", + "columns": [ + { + "expression": "category", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "parts_location_idx": { + "name": "parts_location_idx", + "columns": [ + { + "expression": "location_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "parts_location_id_locations_id_fk": { + "name": "parts_location_id_locations_id_fk", + "tableFrom": "parts", + "tableTo": "locations", + "columnsFrom": [ + "location_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "no action", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.sessions": { + "name": "sessions", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "text", + "primaryKey": true, + "notNull": true + }, + "user_id": { + "name": "user_id", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "expires_at": { + "name": "expires_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true + } + }, + "indexes": {}, + "foreignKeys": { + "sessions_user_id_users_id_fk": { + "name": "sessions_user_id_users_id_fk", + "tableFrom": "sessions", + "tableTo": "users", + "columnsFrom": [ + "user_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.template_items": { + "name": "template_items", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "template_id": { + "name": "template_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "text": { + "name": "text", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "item_type": { + "name": "item_type", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'checkbox'" + }, + "unit": { + "name": "unit", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "sort_order": { + "name": "sort_order", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 0 + } + }, + "indexes": { + "template_items_template_idx": { + "name": "template_items_template_idx", + "columns": [ + { + "expression": "template_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "template_items_template_id_checklist_templates_id_fk": { + "name": "template_items_template_id_checklist_templates_id_fk", + "tableFrom": "template_items", + "tableTo": "checklist_templates", + "columnsFrom": [ + "template_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.todos": { + "name": "todos", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "status": { + "name": "status", + "type": "text", + "primaryKey": false, + "notNull": true, + "default": "'todo'" + }, + "priority": { + "name": "priority", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 2 + }, + "device_id": { + "name": "device_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "due_date": { + "name": "due_date", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "todos_status_idx": { + "name": "todos_status_idx", + "columns": [ + { + "expression": "status", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "todos_priority_idx": { + "name": "todos_priority_idx", + "columns": [ + { + "expression": "priority", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "todos_device_idx": { + "name": "todos_device_idx", + "columns": [ + { + "expression": "device_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "todos_device_id_devices_id_fk": { + "name": "todos_device_id_devices_id_fk", + "tableFrom": "todos", + "tableTo": "devices", + "columnsFrom": [ + "device_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "set null", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": { + "todos_status_check": { + "name": "todos_status_check", + "value": "\"todos\".\"status\" IN ('todo', 'in_progress', 'done')" + }, + "todos_priority_check": { + "name": "todos_priority_check", + "value": "\"todos\".\"priority\" IN (0, 1, 2, 3)" + } + }, + "isRLSEnabled": false + }, + "public.users": { + "name": "users", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "text", + "primaryKey": true, + "notNull": true + }, + "email": { + "name": "email", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "display_name": { + "name": "display_name", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "password_hash": { + "name": "password_hash", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": {}, + "foreignKeys": {}, + "compositePrimaryKeys": {}, + "uniqueConstraints": { + "users_email_unique": { + "name": "users_email_unique", + "nullsNotDistinct": false, + "columns": [ + "email" + ] + } + }, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.wiki_categories": { + "name": "wiki_categories", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "name": { + "name": "name", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "slug": { + "name": "slug", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "description": { + "name": "description", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "sort_order": { + "name": "sort_order", + "type": "integer", + "primaryKey": false, + "notNull": true, + "default": 0 + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": {}, + "foreignKeys": {}, + "compositePrimaryKeys": {}, + "uniqueConstraints": { + "wiki_categories_slug_unique": { + "name": "wiki_categories_slug_unique", + "nullsNotDistinct": false, + "columns": [ + "slug" + ] + } + }, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.wiki_page_tags": { + "name": "wiki_page_tags", + "schema": "", + "columns": { + "page_id": { + "name": "page_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + }, + "tag_id": { + "name": "tag_id", + "type": "uuid", + "primaryKey": false, + "notNull": true + } + }, + "indexes": { + "wiki_page_tags_page_idx": { + "name": "wiki_page_tags_page_idx", + "columns": [ + { + "expression": "page_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "wiki_page_tags_tag_idx": { + "name": "wiki_page_tags_tag_idx", + "columns": [ + { + "expression": "tag_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "wiki_page_tags_page_id_wiki_pages_id_fk": { + "name": "wiki_page_tags_page_id_wiki_pages_id_fk", + "tableFrom": "wiki_page_tags", + "tableTo": "wiki_pages", + "columnsFrom": [ + "page_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + }, + "wiki_page_tags_tag_id_wiki_tags_id_fk": { + "name": "wiki_page_tags_tag_id_wiki_tags_id_fk", + "tableFrom": "wiki_page_tags", + "tableTo": "wiki_tags", + "columnsFrom": [ + "tag_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "cascade", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": {}, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.wiki_pages": { + "name": "wiki_pages", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "title": { + "name": "title", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "slug": { + "name": "slug", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "content": { + "name": "content", + "type": "text", + "primaryKey": false, + "notNull": true + }, + "category_id": { + "name": "category_id", + "type": "uuid", + "primaryKey": false, + "notNull": false + }, + "created_by": { + "name": "created_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "updated_by": { + "name": "updated_by", + "type": "text", + "primaryKey": false, + "notNull": false + }, + "created_at": { + "name": "created_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + }, + "updated_at": { + "name": "updated_at", + "type": "timestamp with time zone", + "primaryKey": false, + "notNull": true, + "default": "now()" + } + }, + "indexes": { + "wiki_pages_category_idx": { + "name": "wiki_pages_category_idx", + "columns": [ + { + "expression": "category_id", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + }, + "wiki_pages_slug_idx": { + "name": "wiki_pages_slug_idx", + "columns": [ + { + "expression": "slug", + "isExpression": false, + "asc": true, + "nulls": "last" + } + ], + "isUnique": false, + "concurrently": false, + "method": "btree", + "with": {} + } + }, + "foreignKeys": { + "wiki_pages_category_id_wiki_categories_id_fk": { + "name": "wiki_pages_category_id_wiki_categories_id_fk", + "tableFrom": "wiki_pages", + "tableTo": "wiki_categories", + "columnsFrom": [ + "category_id" + ], + "columnsTo": [ + "id" + ], + "onDelete": "set null", + "onUpdate": "no action" + } + }, + "compositePrimaryKeys": {}, + "uniqueConstraints": { + "wiki_pages_slug_unique": { + "name": "wiki_pages_slug_unique", + "nullsNotDistinct": false, + "columns": [ + "slug" + ] + } + }, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + }, + "public.wiki_tags": { + "name": "wiki_tags", + "schema": "", + "columns": { + "id": { + "name": "id", + "type": "uuid", + "primaryKey": true, + "notNull": true, + "default": "gen_random_uuid()" + }, + "name": { + "name": "name", + "type": "text", + "primaryKey": false, + "notNull": true + } + }, + "indexes": {}, + "foreignKeys": {}, + "compositePrimaryKeys": {}, + "uniqueConstraints": { + "wiki_tags_name_unique": { + "name": "wiki_tags_name_unique", + "nullsNotDistinct": false, + "columns": [ + "name" + ] + } + }, + "policies": {}, + "checkConstraints": {}, + "isRLSEnabled": false + } + }, + "enums": {}, + "schemas": {}, + "sequences": {}, + "roles": {}, + "policies": {}, + "views": {}, + "_meta": { + "columns": {}, + "schemas": {}, + "tables": {} + } +} \ No newline at end of file diff --git a/drizzle/migrations/meta/_journal.json b/drizzle/migrations/meta/_journal.json index 7af1473..33782c3 100644 --- a/drizzle/migrations/meta/_journal.json +++ b/drizzle/migrations/meta/_journal.json @@ -8,6 +8,13 @@ "when": 1782725202288, "tag": "0000_clear_sister_grimm", "breakpoints": true + }, + { + "idx": 1, + "version": "7", + "when": 1782726648360, + "tag": "0001_rainy_rictor", + "breakpoints": true } ] } \ No newline at end of file diff --git a/src/lib/server/db/schema.ts b/src/lib/server/db/schema.ts index db08b5f..10ade18 100644 --- a/src/lib/server/db/schema.ts +++ b/src/lib/server/db/schema.ts @@ -5,6 +5,7 @@ import { integer, boolean, timestamp, + doublePrecision, index, check } from 'drizzle-orm/pg-core'; @@ -383,6 +384,7 @@ export const parts = pgTable( category: text('category').notNull(), mpn: text('mpn'), value: text('value'), + valueNumeric: doublePrecision('value_numeric'), voltage: text('voltage'), tolerance: text('tolerance'), power: text('power'), diff --git a/src/lib/utils/valueParser.ts b/src/lib/utils/valueParser.ts new file mode 100644 index 0000000..3b8fcf5 --- /dev/null +++ b/src/lib/utils/valueParser.ts @@ -0,0 +1,32 @@ +const PREFIX: Record = { + p: 1e-12, + n: 1e-9, + u: 1e-6, + µ: 1e-6, + m: 1e-3, + k: 1e3, + K: 1e3, + M: 1e6, + G: 1e9 +}; + +// Parses a human value string into a base-SI number (Farads, Ohms, Henrys, Hz). +// Returns null if unparseable (e.g. part codes like "BC547", "1N4148"). +export function parseValueNumeric(value: string | null | undefined): number | null { + if (!value) return null; + + const s = value.trim(); + + // Match: digits, optional decimal, optional SI prefix, optional unit letters + // Handles: "100µF", "10kΩ", "4.7uH", "32.768kHz", "47R", "1M", "220" + const match = s.match(/^([0-9]+(?:\.[0-9]+)?)\s*([pnuµmkKMG]?)\s*([FHhzΩRω]|Hz|hz|Ohm|ohm)?/i); + if (!match) return null; + + const num = parseFloat(match[1]); + if (isNaN(num)) return null; + + const prefix = match[2] ?? ''; + const mult = PREFIX[prefix] ?? 1; + + return num * mult; +} diff --git a/src/routes/(app)/parts/+page.server.ts b/src/routes/(app)/parts/+page.server.ts index c0121f3..d186f0b 100644 --- a/src/routes/(app)/parts/+page.server.ts +++ b/src/routes/(app)/parts/+page.server.ts @@ -1,12 +1,13 @@ import type { PageServerLoad } from './$types'; import { db } from '$lib/server/db/index.js'; import { parts, locations } from '$lib/server/db/schema.js'; -import { eq, ilike, or, and, count } from 'drizzle-orm'; +import { eq, ilike, or, and, count, asc, sql } from 'drizzle-orm'; export const load: PageServerLoad = async ({ url }) => { const category = url.searchParams.get('category'); const mounting = url.searchParams.get('mounting'); const search = url.searchParams.get('q'); + const sort = url.searchParams.get('sort') ?? 'category'; // 'category' | 'value' const page = Math.max(1, Number(url.searchParams.get('page') ?? 1)); const pageSize = 48; @@ -28,6 +29,11 @@ export const load: PageServerLoad = async ({ url }) => { const [totalResult] = await db.select({ value: count() }).from(parts).where(where); + const orderBy = + sort === 'value' + ? [asc(parts.category), sql`${parts.valueNumeric} ASC NULLS LAST`, asc(parts.value)] + : [asc(parts.category), asc(parts.value)]; + const partList = await db .select({ id: parts.id, @@ -35,6 +41,7 @@ export const load: PageServerLoad = async ({ url }) => { category: parts.category, mpn: parts.mpn, value: parts.value, + valueNumeric: parts.valueNumeric, voltage: parts.voltage, tolerance: parts.tolerance, power: parts.power, @@ -47,7 +54,7 @@ export const load: PageServerLoad = async ({ url }) => { .from(parts) .leftJoin(locations, eq(parts.locationId, locations.id)) .where(where) - .orderBy(parts.category, parts.value) + .orderBy(...orderBy) .limit(pageSize) .offset((page - 1) * pageSize); @@ -56,6 +63,6 @@ export const load: PageServerLoad = async ({ url }) => { total: totalResult?.value ?? 0, page, pageSize, - filters: { category, mounting, search } + filters: { category, mounting, search, sort } }; }; diff --git a/src/routes/(app)/parts/+page.svelte b/src/routes/(app)/parts/+page.svelte index ac9e9dd..46bf08b 100644 --- a/src/routes/(app)/parts/+page.svelte +++ b/src/routes/(app)/parts/+page.svelte @@ -21,6 +21,7 @@ } const totalPages = $derived(Math.ceil(data.total / data.pageSize)); + const sortedByValue = $derived(data.filters.sort === 'value'); function mountingColor(mounting: string | null) { if (mounting === 'SMT') return 'bg-purple-100 text-purple-700 dark:bg-purple-900/40 dark:text-purple-300'; @@ -66,6 +67,16 @@ +
+ + +

{data.total} part{data.total !== 1 ? 's' : ''}

diff --git a/src/routes/(app)/parts/[id]/edit/+page.server.ts b/src/routes/(app)/parts/[id]/edit/+page.server.ts index 8307404..c5baa20 100644 --- a/src/routes/(app)/parts/[id]/edit/+page.server.ts +++ b/src/routes/(app)/parts/[id]/edit/+page.server.ts @@ -4,6 +4,7 @@ import { parts, locations } from '$lib/server/db/schema.js'; import { eq, sql } from 'drizzle-orm'; import { error, fail, redirect } from '@sveltejs/kit'; import { z } from 'zod'; +import { parseValueNumeric } from '$lib/utils/valueParser.js'; const partSchema = z.object({ name: z.string().optional(), @@ -56,6 +57,7 @@ export const actions: Actions = { category: data.category, mpn: data.mpn || null, value: data.value || null, + valueNumeric: parseValueNumeric(data.value), voltage: data.voltage || null, tolerance: data.tolerance || null, power: data.power || null, diff --git a/src/routes/(app)/parts/new/+page.server.ts b/src/routes/(app)/parts/new/+page.server.ts index 111b6cf..6130c1b 100644 --- a/src/routes/(app)/parts/new/+page.server.ts +++ b/src/routes/(app)/parts/new/+page.server.ts @@ -3,6 +3,7 @@ import { db } from '$lib/server/db/index.js'; import { parts, locations } from '$lib/server/db/schema.js'; import { fail, redirect } from '@sveltejs/kit'; import { z } from 'zod'; +import { parseValueNumeric } from '$lib/utils/valueParser.js'; const partSchema = z.object({ name: z.string().optional(), @@ -47,6 +48,7 @@ export const actions: Actions = { category: data.category, mpn: data.mpn || null, value: data.value || null, + valueNumeric: parseValueNumeric(data.value), voltage: data.voltage || null, tolerance: data.tolerance || null, power: data.power || null,