@@ -5,8 +5,10 @@ package disk
55
66import (
77 "context"
8+ "encoding/json"
89 "errors"
910 "fmt"
11+ "strings"
1012 "unsafe"
1113
1214 "golang.org/x/sys/unix"
@@ -88,8 +90,58 @@ func getFsType(stat unix.Statfs_t) string {
8890 return common .ByteToString (stat .Fstypename [:])
8991}
9092
91- func SerialNumberWithContext (_ context.Context , _ string ) (string , error ) {
92- return "" , common .ErrNotImplementedError
93+ type spnvmeDataTypeItem struct {
94+ Name string `json:"_name"`
95+ BsdName string `json:"bsd_name"`
96+ DetachableDrive string `json:"detachable_drive"`
97+ DeviceModel string `json:"device_model"`
98+ DeviceRevision string `json:"device_revision"`
99+ DeviceSerial string `json:"device_serial"`
100+ PartitionMapType string `json:"partition_map_type"`
101+ RemovableMedia string `json:"removable_media"`
102+ Size string `json:"size"`
103+ SizeInBytes int64 `json:"size_in_bytes"`
104+ SmartStatus string `json:"smart_status"`
105+ SpnvmeTrimSupport string `json:"spnvme_trim_support"`
106+ Volumes []struct {
107+ Name string `json:"_name"`
108+ BsdName string `json:"bsd_name"`
109+ Iocontent string `json:"iocontent"`
110+ Size string `json:"size"`
111+ SizeInBytes int `json:"size_in_bytes"`
112+ } `json:"volumes"`
113+ }
114+
115+ type spnvmeDataWrapper struct {
116+ SPNVMeDataType []struct {
117+ Items []spnvmeDataTypeItem `json:"_items"`
118+ } `json:"SPNVMeDataType"`
119+ }
120+
121+ func SerialNumberWithContext (ctx context.Context , _ string ) (string , error ) {
122+ output , err := invoke .CommandWithContext (ctx , "system_profiler" , "SPNVMeDataType" , "-json" )
123+ if err != nil {
124+ return "" , err
125+ }
126+
127+ var data spnvmeDataWrapper
128+ if err := json .Unmarshal (output , & data ); err != nil {
129+ return "" , fmt .Errorf ("failed to unmarshal JSON: %w" , err )
130+ }
131+
132+ // Extract all serial numbers into a single string
133+ var serialNumbers []string
134+ for _ , spnvmeData := range data .SPNVMeDataType {
135+ for _ , item := range spnvmeData .Items {
136+ serialNumbers = append (serialNumbers , item .DeviceSerial )
137+ }
138+ }
139+
140+ if len (serialNumbers ) == 0 {
141+ return "" , errors .New ("no serial numbers found" )
142+ }
143+
144+ return strings .Join (serialNumbers , ", " ), nil
93145}
94146
95147func LabelWithContext (_ context.Context , _ string ) (string , error ) {
0 commit comments