mirror of
https://github.com/JustKato/drive-health.git
synced 2026-04-30 01:42:29 +03:00
Started moving to a sqlite3 implementation
This commit is contained in:
@@ -6,9 +6,12 @@ import (
|
||||
"fmt"
|
||||
"os/exec"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
func GetSystemHardDrives() ([]*HardDrive, error) {
|
||||
func GetSystemHardDrives(db *gorm.DB, olderThan *time.Time, newerThan *time.Time) ([]*HardDrive, error) {
|
||||
|
||||
// Execute the lsblk command to get detailed block device information
|
||||
cmd := exec.Command("lsblk", "-d", "-o", "NAME,TRAN,SIZE,MODEL,SERIAL,TYPE")
|
||||
@@ -20,7 +23,7 @@ func GetSystemHardDrives() ([]*HardDrive, error) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
var hardDrives []*HardDrive
|
||||
var systemHardDrives []*HardDrive
|
||||
|
||||
// Scan the output line by line
|
||||
scanner := bufio.NewScanner(&out)
|
||||
@@ -39,17 +42,16 @@ func GetSystemHardDrives() ([]*HardDrive, error) {
|
||||
}
|
||||
|
||||
// Filter out nvme drives (M.2)
|
||||
if cols[1] != "nvme" && cols[5] != "Device" {
|
||||
if cols[1] != "nvme" && cols[5] != "Device" && cols[1] != "usb" {
|
||||
hd := &HardDrive{
|
||||
Name: cols[0],
|
||||
Transport: cols[1],
|
||||
Size: cols[2],
|
||||
Model: cols[3],
|
||||
Serial: cols[4],
|
||||
Type: cols[5],
|
||||
Temperature: 0,
|
||||
Name: cols[0],
|
||||
Transport: cols[1],
|
||||
Size: cols[2],
|
||||
Model: cols[3],
|
||||
Serial: cols[4],
|
||||
Type: cols[5],
|
||||
}
|
||||
hardDrives = append(hardDrives, hd)
|
||||
systemHardDrives = append(systemHardDrives, hd)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -58,5 +60,35 @@ func GetSystemHardDrives() ([]*HardDrive, error) {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return hardDrives, nil
|
||||
var updatedHardDrives []*HardDrive
|
||||
|
||||
for _, sysHDD := range systemHardDrives {
|
||||
var existingHD HardDrive
|
||||
q := db.Where("serial = ?", sysHDD.Serial)
|
||||
|
||||
if newerThan != nil && olderThan != nil {
|
||||
fmt.Printf("\nNewer Than: %s\n", newerThan)
|
||||
fmt.Printf("Older Than: %s\n\n", olderThan)
|
||||
q = q.Preload("Temperatures", "time_stamp < ? AND time_stamp > ?", newerThan, olderThan)
|
||||
}
|
||||
|
||||
result := q.First(&existingHD)
|
||||
|
||||
if result.Error == gorm.ErrRecordNotFound {
|
||||
// Hard drive not found, create new
|
||||
db.Create(&sysHDD)
|
||||
updatedHardDrives = append(updatedHardDrives, sysHDD)
|
||||
} else {
|
||||
// Hard drive found, update existing
|
||||
existingHD.Name = sysHDD.Name
|
||||
existingHD.Transport = sysHDD.Transport
|
||||
existingHD.Size = sysHDD.Size
|
||||
existingHD.Model = sysHDD.Model
|
||||
existingHD.Type = sysHDD.Type
|
||||
db.Save(&existingHD)
|
||||
updatedHardDrives = append(updatedHardDrives, &existingHD)
|
||||
}
|
||||
}
|
||||
|
||||
return updatedHardDrives, nil
|
||||
}
|
||||
|
||||
64
lib/hardware/models.go
Normal file
64
lib/hardware/models.go
Normal file
@@ -0,0 +1,64 @@
|
||||
package hardware
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"github.com/anatol/smart.go"
|
||||
"gorm.io/gorm"
|
||||
)
|
||||
|
||||
type HardDrive struct {
|
||||
ID uint `gorm:"primarykey"`
|
||||
CreatedAt time.Time
|
||||
UpdatedAt time.Time
|
||||
DeletedAt gorm.DeletedAt `gorm:"index"`
|
||||
Name string
|
||||
Transport string
|
||||
Size string
|
||||
Model string
|
||||
Serial string
|
||||
Type string
|
||||
Temperatures []HardDriveTemperature `gorm:"foreignKey:HardDriveID"`
|
||||
}
|
||||
|
||||
type HardDriveTemperature struct {
|
||||
gorm.Model
|
||||
HardDriveID uint
|
||||
TimeStamp time.Time
|
||||
Temperature int
|
||||
}
|
||||
|
||||
// A snapshot in time of the current state of the harddrives
|
||||
type HardwareSnapshot struct {
|
||||
TimeStamp time.Time
|
||||
HDD []*HardDrive
|
||||
}
|
||||
|
||||
type Snapshots struct {
|
||||
List []*HardwareSnapshot
|
||||
}
|
||||
|
||||
// Fetch the temperature of the device, optinally update the reference object
|
||||
func (h *HardDrive) GetTemperature() int {
|
||||
// Fetch the device by name
|
||||
disk, err := smart.Open("/dev/" + h.Name)
|
||||
if err != nil {
|
||||
fmt.Printf("Failed to open device %s: %s\n", h.Name, err)
|
||||
return -1
|
||||
}
|
||||
defer disk.Close()
|
||||
|
||||
// Fetch SMART data
|
||||
smartInfo, err := disk.ReadGenericAttributes()
|
||||
if err != nil {
|
||||
fmt.Printf("Failed to get SMART data for %s: %s\n", h.Name, err)
|
||||
return -1
|
||||
}
|
||||
|
||||
// Parse the temperature
|
||||
temperature := int(smartInfo.Temperature)
|
||||
|
||||
// Return the found value
|
||||
return temperature
|
||||
}
|
||||
@@ -1,46 +0,0 @@
|
||||
package hardware
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
|
||||
"github.com/anatol/smart.go"
|
||||
)
|
||||
|
||||
type HardDrive struct {
|
||||
Name string
|
||||
Transport string
|
||||
Size string
|
||||
Model string
|
||||
Serial string
|
||||
Type string
|
||||
Temperature int
|
||||
}
|
||||
|
||||
// Fetch the temperature of the device, optinally update the reference object
|
||||
func (h *HardDrive) GetTemperature(updateTemp bool) int {
|
||||
// Fetch the device by name
|
||||
disk, err := smart.Open("/dev/" + h.Name)
|
||||
if err != nil {
|
||||
fmt.Printf("Failed to open device %s: %s\n", h.Name, err)
|
||||
return -1
|
||||
}
|
||||
defer disk.Close()
|
||||
|
||||
// Fetch SMART data
|
||||
smartInfo, err := disk.ReadGenericAttributes()
|
||||
if err != nil {
|
||||
fmt.Printf("Failed to get SMART data for %s: %s\n", h.Name, err)
|
||||
return -1
|
||||
}
|
||||
|
||||
// Parse the temperature
|
||||
temperature := int(smartInfo.Temperature)
|
||||
|
||||
// Optionally update the reference object's temperature
|
||||
if updateTemp {
|
||||
h.Temperature = temperature
|
||||
}
|
||||
|
||||
// Return the found value
|
||||
return temperature
|
||||
}
|
||||
Reference in New Issue
Block a user