Repository: 1Password/typeshare (rust)

Issue:
Support for unit structs
Hi,

Currently, unit structs are not supported:

```rust
#[derive(Debug, serde::Serialize)]
#[typeshare::typeshare]
pub struct MyType;
```

(Error: `unit structs are currently unsupported`)

A workaround is to create a tuple struct with a tuple as argument (tuple structs without an argument result in another error):

```rust
#[derive(Debug, serde::Serialize)]
#[typeshare::typeshare]
pub struct MyType(pub ());
```

However, this is ugly and results in the following code being generated (Typescript):

```typescript
export type MyType = undefined;
```

I'm a Typescript beginner, but this doesn't look great. I think, it would be better to have something like:

```typescript
export type MyType = "MyType";
```

(I'm not saying that `struct MyType(());` should result in the above, but that `struct MyType;` should be supported, which would generate it).


Pull request description:
Support unit structs that don't use bracket syntax
This PR will add support for unit structs that use semicolon syntax instead of bracket syntax.

In other words,
```rust
#[typeshare]
struct UnitStruct;
```
will now work properly.

This closes #41 

Patch:
diff --git a/core/src/parser.rs b/core/src/parser.rs
index 4cd8638..68ab054 100644
--- a/core/src/parser.rs
+++ b/core/src/parser.rs
@@ -54,8 +54,6 @@ pub enum ParseError {
     UnsupportedType(String),
     #[error("tuple structs with more than one field are currently unsupported")]
     ComplexTupleStruct,
-    #[error("unit structs are currently unsupported")]
-    UnitStruct,
     #[error("multiple unnamed associated types are not currently supported")]
     MultipleUnnamedAssociatedTypes,
     #[error("the serde tag attribute is not supported for non-algebraic enums: {enum_ident}")]
@@ -191,7 +189,13 @@ fn parse_struct(s: &ItemStruct) -> Result<RustThing, ParseError> {
             })
         }
         // Unit structs or `None`
-        Fields::Unit => return Err(ParseError::UnitStruct),
+        Fields::Unit => RustThing::Struct(RustStruct {
+            id: get_ident(Some(&s.ident), &s.attrs, &None),
+            generic_types,
+            fields: vec![],
+            comments: parse_comment_attrs(&s.attrs),
+            decorators: get_decorators(&s.attrs),
+        }),
     })
 }
 


Test patch:
diff --git a/core/data/tests/can_generate_unit_structs/input.rs b/core/data/tests/can_generate_unit_structs/input.rs
new file mode 100644
index 0000000..623ae34
--- /dev/null
+++ b/core/data/tests/can_generate_unit_structs/input.rs
@@ -0,0 +1,4 @@
+// This test verifies that unit structs created without bracket syntax can still be generated.
+
+#[typeshare]
+struct UnitStruct;
\ No newline at end of file
diff --git a/core/data/tests/can_generate_unit_structs/output.go b/core/data/tests/can_generate_unit_structs/output.go
new file mode 100644
index 0000000..308e1a0
--- /dev/null
+++ b/core/data/tests/can_generate_unit_structs/output.go
@@ -0,0 +1,7 @@
+// Code generated by typeshare 1.0.0. DO NOT EDIT.
+package proto
+
+import "encoding/json"
+
+type UnitStruct struct {
+}
diff --git a/core/data/tests/can_generate_unit_structs/output.kt b/core/data/tests/can_generate_unit_structs/output.kt
new file mode 100644
index 0000000..45242c6
--- /dev/null
+++ b/core/data/tests/can_generate_unit_structs/output.kt
@@ -0,0 +1,14 @@
+/**
+ * Generated by typeshare 1.0.0
+ */
+
+@file:NoLiveLiterals
+
+package com.agilebits.onepassword
+
+import androidx.compose.runtime.NoLiveLiterals
+import kotlinx.serialization.*
+
+@Serializable
+class UnitStruct
+
diff --git a/core/data/tests/can_generate_unit_structs/output.swift b/core/data/tests/can_generate_unit_structs/output.swift
new file mode 100644
index 0000000..3d957c0
--- /dev/null
+++ b/core/data/tests/can_generate_unit_structs/output.swift
@@ -0,0 +1,9 @@
+/*
+ Generated by typeshare 1.0.0
+ */
+
+import Foundation
+
+public struct UnitStruct: Codable {
+	public init() {}
+}
diff --git a/core/data/tests/can_generate_unit_structs/output.ts b/core/data/tests/can_generate_unit_structs/output.ts
new file mode 100644
index 0000000..25b81aa
--- /dev/null
+++ b/core/data/tests/can_generate_unit_structs/output.ts
@@ -0,0 +1,7 @@
+/*
+ Generated by typeshare 1.0.0
+*/
+
+export interface UnitStruct {
+}
+
diff --git a/core/tests/snapshot_tests.rs b/core/tests/snapshot_tests.rs
index 3c0099f..12bf66e 100644
--- a/core/tests/snapshot_tests.rs
+++ b/core/tests/snapshot_tests.rs
@@ -451,6 +451,7 @@ tests! {
     ];
     can_handle_serde_rename_all: [swift, kotlin, typescript, go];
     can_handle_serde_rename_on_top_level: [swift { prefix: "OP".to_string(), }, kotlin, typescript, go];
+    can_generate_unit_structs: [swift, kotlin, typescript, go];
     kebab_case_rename: [swift, kotlin, typescript, go];
 
     /// Other