Compare commits

...

12 Commits

Author SHA1 Message Date
henrygd
fca13004bd release 0.12.9 2025-09-17 16:06:20 -04:00
henrygd
376a86829c fix divide by zero error (#1175) 2025-09-17 16:00:50 -04:00
henrygd
ef48613f3f improve style of chart sheet button on mobile
- also update changelog
2025-09-17 15:13:10 -04:00
henrygd
49976c6f61 fix nvidia agent dockerfile after project reorganization 2025-09-17 14:10:02 -04:00
henrygd
d68f1f0985 0.12.8 release :) 2025-09-17 14:02:17 -04:00
henrygd
273a090200 update translations 2025-09-17 14:01:20 -04:00
henrygd
59057a2ba4 add check for status alerts which are not properly resolved (#1052) 2025-09-17 13:31:49 -04:00
henrygd
1b9e781d45 refactor deltatracker
- embed mutex
- add example function
2025-09-16 22:09:46 -04:00
henrygd
4e0ca7c2ba formatting (biome) 2025-09-15 18:04:13 -04:00
henrygd
a9e7bcd37f add per-interface and cumulative network traffic charts (#926)
Co-authored-by: Sven van Ginkel <svenvanginkel@icloud.com>
2025-09-15 17:59:21 -04:00
henrygd
4635f24fb2 fix entre arg in makefile dev server 2025-09-15 17:26:07 -04:00
henrygd
3e73399b87 fix battery detection on newer macs (#1170) 2025-09-15 12:02:50 -04:00
82 changed files with 2949 additions and 568 deletions

View File

@@ -77,7 +77,7 @@ dev-hub: export ENV=dev
dev-hub: dev-hub:
mkdir -p ./internal/site/dist && touch ./internal/site/dist/index.html mkdir -p ./internal/site/dist && touch ./internal/site/dist/index.html
@if command -v entr >/dev/null 2>&1; then \ @if command -v entr >/dev/null 2>&1; then \
find ./internal/cmd/hub/*.go ./internal/{alerts,hub,records,users}/*.go | entr -r -s "cd ./internal/cmd/hub && go run -tags development . serve --http 0.0.0.0:8090"; \ find ./internal -type f -name '*.go' | entr -r -s "cd ./internal/cmd/hub && go run -tags development . serve --http 0.0.0.0:8090"; \
else \ else \
cd ./internal/cmd/hub && go run -tags development . serve --http 0.0.0.0:8090; \ cd ./internal/cmd/hub && go run -tags development . serve --http 0.0.0.0:8090; \
fi fi

View File

@@ -20,9 +20,8 @@ func HasReadableBattery() bool {
} }
haveCheckedBattery = true haveCheckedBattery = true
bat, err := battery.Get(0) bat, err := battery.Get(0)
if err == nil && bat != nil { systemHasBattery = err == nil && bat != nil && bat.Design != 0 && bat.Full != 0
systemHasBattery = true if !systemHasBattery {
} else {
slog.Debug("No battery found", "err", err) slog.Debug("No battery found", "err", err)
} }
return systemHasBattery return systemHasBattery

View File

@@ -0,0 +1,81 @@
// Package deltatracker provides a tracker for calculating differences in numeric values over time.
package deltatracker
import (
"sync"
"golang.org/x/exp/constraints"
)
// Numeric is a constraint that permits any integer or floating-point type.
type Numeric interface {
constraints.Integer | constraints.Float
}
// DeltaTracker is a generic, thread-safe tracker for calculating differences
// in numeric values over time.
// K is the key type (e.g., int, string).
// V is the value type (e.g., int, int64, float32, float64).
type DeltaTracker[K comparable, V Numeric] struct {
sync.RWMutex
current map[K]V
previous map[K]V
}
// NewDeltaTracker creates a new generic tracker.
func NewDeltaTracker[K comparable, V Numeric]() *DeltaTracker[K, V] {
return &DeltaTracker[K, V]{
current: make(map[K]V),
previous: make(map[K]V),
}
}
// Set records the current value for a given ID.
func (t *DeltaTracker[K, V]) Set(id K, value V) {
t.Lock()
defer t.Unlock()
t.current[id] = value
}
// Deltas returns a map of all calculated deltas for the current interval.
func (t *DeltaTracker[K, V]) Deltas() map[K]V {
t.RLock()
defer t.RUnlock()
deltas := make(map[K]V)
for id, currentVal := range t.current {
if previousVal, ok := t.previous[id]; ok {
deltas[id] = currentVal - previousVal
} else {
deltas[id] = 0
}
}
return deltas
}
// Delta returns the delta for a single key.
// Returns 0 if the key doesn't exist or has no previous value.
func (t *DeltaTracker[K, V]) Delta(id K) V {
t.RLock()
defer t.RUnlock()
currentVal, currentOk := t.current[id]
if !currentOk {
return 0
}
previousVal, previousOk := t.previous[id]
if !previousOk {
return 0
}
return currentVal - previousVal
}
// Cycle prepares the tracker for the next interval.
func (t *DeltaTracker[K, V]) Cycle() {
t.Lock()
defer t.Unlock()
t.previous = t.current
t.current = make(map[K]V)
}

View File

@@ -0,0 +1,217 @@
package deltatracker
import (
"fmt"
"testing"
"github.com/stretchr/testify/assert"
)
func ExampleDeltaTracker() {
tracker := NewDeltaTracker[string, int]()
tracker.Set("key1", 10)
tracker.Set("key2", 20)
tracker.Cycle()
tracker.Set("key1", 15)
tracker.Set("key2", 30)
fmt.Println(tracker.Delta("key1"))
fmt.Println(tracker.Delta("key2"))
fmt.Println(tracker.Deltas())
// Output: 5
// 10
// map[key1:5 key2:10]
}
func TestNewDeltaTracker(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
assert.NotNil(t, tracker)
assert.Empty(t, tracker.current)
assert.Empty(t, tracker.previous)
}
func TestSet(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
tracker.Set("key1", 10)
tracker.RLock()
defer tracker.RUnlock()
assert.Equal(t, 10, tracker.current["key1"])
}
func TestDeltas(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
// Test with no previous values
tracker.Set("key1", 10)
tracker.Set("key2", 20)
deltas := tracker.Deltas()
assert.Equal(t, 0, deltas["key1"])
assert.Equal(t, 0, deltas["key2"])
// Cycle to move current to previous
tracker.Cycle()
// Set new values and check deltas
tracker.Set("key1", 15) // Delta should be 5 (15-10)
tracker.Set("key2", 25) // Delta should be 5 (25-20)
tracker.Set("key3", 30) // New key, delta should be 0
deltas = tracker.Deltas()
assert.Equal(t, 5, deltas["key1"])
assert.Equal(t, 5, deltas["key2"])
assert.Equal(t, 0, deltas["key3"])
}
func TestCycle(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
tracker.Set("key1", 10)
tracker.Set("key2", 20)
// Verify current has values
tracker.RLock()
assert.Equal(t, 10, tracker.current["key1"])
assert.Equal(t, 20, tracker.current["key2"])
assert.Empty(t, tracker.previous)
tracker.RUnlock()
tracker.Cycle()
// After cycle, previous should have the old current values
// and current should be empty
tracker.RLock()
assert.Empty(t, tracker.current)
assert.Equal(t, 10, tracker.previous["key1"])
assert.Equal(t, 20, tracker.previous["key2"])
tracker.RUnlock()
}
func TestCompleteWorkflow(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
// First interval
tracker.Set("server1", 100)
tracker.Set("server2", 200)
// Get deltas for first interval (should be zero)
firstDeltas := tracker.Deltas()
assert.Equal(t, 0, firstDeltas["server1"])
assert.Equal(t, 0, firstDeltas["server2"])
// Cycle to next interval
tracker.Cycle()
// Second interval
tracker.Set("server1", 150) // Delta: 50
tracker.Set("server2", 180) // Delta: -20
tracker.Set("server3", 300) // New server, delta: 300
secondDeltas := tracker.Deltas()
assert.Equal(t, 50, secondDeltas["server1"])
assert.Equal(t, -20, secondDeltas["server2"])
assert.Equal(t, 0, secondDeltas["server3"])
}
func TestDeltaTrackerWithDifferentTypes(t *testing.T) {
// Test with int64
intTracker := NewDeltaTracker[string, int64]()
intTracker.Set("pid1", 1000)
intTracker.Cycle()
intTracker.Set("pid1", 1200)
intDeltas := intTracker.Deltas()
assert.Equal(t, int64(200), intDeltas["pid1"])
// Test with float64
floatTracker := NewDeltaTracker[string, float64]()
floatTracker.Set("cpu1", 1.5)
floatTracker.Cycle()
floatTracker.Set("cpu1", 2.7)
floatDeltas := floatTracker.Deltas()
assert.InDelta(t, 1.2, floatDeltas["cpu1"], 0.0001)
// Test with int keys
pidTracker := NewDeltaTracker[int, int64]()
pidTracker.Set(101, 20000)
pidTracker.Cycle()
pidTracker.Set(101, 22500)
pidDeltas := pidTracker.Deltas()
assert.Equal(t, int64(2500), pidDeltas[101])
}
func TestDelta(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
// Test getting delta for non-existent key
result := tracker.Delta("nonexistent")
assert.Equal(t, 0, result)
// Test getting delta for key with no previous value
tracker.Set("key1", 10)
result = tracker.Delta("key1")
assert.Equal(t, 0, result)
// Cycle to move current to previous
tracker.Cycle()
// Test getting delta for key with previous value
tracker.Set("key1", 15)
result = tracker.Delta("key1")
assert.Equal(t, 5, result)
// Test getting delta for key that exists in previous but not current
result = tracker.Delta("key1")
assert.Equal(t, 5, result) // Should still return 5
// Test getting delta for key that exists in current but not previous
tracker.Set("key2", 20)
result = tracker.Delta("key2")
assert.Equal(t, 0, result)
}
func TestDeltaWithDifferentTypes(t *testing.T) {
// Test with int64
intTracker := NewDeltaTracker[string, int64]()
intTracker.Set("pid1", 1000)
intTracker.Cycle()
intTracker.Set("pid1", 1200)
result := intTracker.Delta("pid1")
assert.Equal(t, int64(200), result)
// Test with float64
floatTracker := NewDeltaTracker[string, float64]()
floatTracker.Set("cpu1", 1.5)
floatTracker.Cycle()
floatTracker.Set("cpu1", 2.7)
floatResult := floatTracker.Delta("cpu1")
assert.InDelta(t, 1.2, floatResult, 0.0001)
// Test with int keys
pidTracker := NewDeltaTracker[int, int64]()
pidTracker.Set(101, 20000)
pidTracker.Cycle()
pidTracker.Set(101, 22500)
pidResult := pidTracker.Delta(101)
assert.Equal(t, int64(2500), pidResult)
}
func TestDeltaConcurrentAccess(t *testing.T) {
tracker := NewDeltaTracker[string, int]()
// Set initial values
tracker.Set("key1", 10)
tracker.Set("key2", 20)
tracker.Cycle()
// Set new values
tracker.Set("key1", 15)
tracker.Set("key2", 25)
// Test concurrent access safety
result1 := tracker.Delta("key1")
result2 := tracker.Delta("key2")
assert.Equal(t, 5, result1)
assert.Equal(t, 5, result2)
}

View File

@@ -1,13 +1,86 @@
package agent package agent
import ( import (
"fmt"
"log/slog" "log/slog"
"strings" "strings"
"time" "time"
"github.com/henrygd/beszel/internal/entities/system"
psutilNet "github.com/shirou/gopsutil/v4/net" psutilNet "github.com/shirou/gopsutil/v4/net"
) )
func (a *Agent) updateNetworkStats(systemStats *system.Stats) {
// network stats
if len(a.netInterfaces) == 0 {
// if no network interfaces, initialize again
// this is a fix if agent started before network is online (#466)
// maybe refactor this in the future to not cache interface names at all so we
// don't miss an interface that's been added after agent started in any circumstance
a.initializeNetIoStats()
}
if systemStats.NetworkInterfaces == nil {
systemStats.NetworkInterfaces = make(map[string][4]uint64, 0)
}
if netIO, err := psutilNet.IOCounters(true); err == nil {
msElapsed := uint64(time.Since(a.netIoStats.Time).Milliseconds())
a.netIoStats.Time = time.Now()
totalBytesSent := uint64(0)
totalBytesRecv := uint64(0)
netInterfaceDeltaTracker.Cycle()
// sum all bytes sent and received
for _, v := range netIO {
// skip if not in valid network interfaces list
if _, exists := a.netInterfaces[v.Name]; !exists {
continue
}
totalBytesSent += v.BytesSent
totalBytesRecv += v.BytesRecv
// track deltas for each network interface
netInterfaceDeltaTracker.Set(fmt.Sprintf("%sdown", v.Name), v.BytesRecv)
netInterfaceDeltaTracker.Set(fmt.Sprintf("%sup", v.Name), v.BytesSent)
var upDelta, downDelta uint64
if msElapsed > 0 {
upDelta = netInterfaceDeltaTracker.Delta(fmt.Sprintf("%sup", v.Name)) * 1000 / msElapsed
downDelta = netInterfaceDeltaTracker.Delta(fmt.Sprintf("%sdown", v.Name)) * 1000 / msElapsed
}
// add interface to systemStats
systemStats.NetworkInterfaces[v.Name] = [4]uint64{upDelta, downDelta, v.BytesSent, v.BytesRecv}
}
// add to systemStats
var bytesSentPerSecond, bytesRecvPerSecond uint64
if msElapsed > 0 {
bytesSentPerSecond = (totalBytesSent - a.netIoStats.BytesSent) * 1000 / msElapsed
bytesRecvPerSecond = (totalBytesRecv - a.netIoStats.BytesRecv) * 1000 / msElapsed
}
networkSentPs := bytesToMegabytes(float64(bytesSentPerSecond))
networkRecvPs := bytesToMegabytes(float64(bytesRecvPerSecond))
// add check for issue (#150) where sent is a massive number
if networkSentPs > 10_000 || networkRecvPs > 10_000 {
slog.Warn("Invalid net stats. Resetting.", "sent", networkSentPs, "recv", networkRecvPs)
for _, v := range netIO {
if _, exists := a.netInterfaces[v.Name]; !exists {
continue
}
slog.Info(v.Name, "recv", v.BytesRecv, "sent", v.BytesSent)
}
// reset network I/O stats
a.initializeNetIoStats()
} else {
systemStats.NetworkSent = networkSentPs
systemStats.NetworkRecv = networkRecvPs
systemStats.Bandwidth[0], systemStats.Bandwidth[1] = bytesSentPerSecond, bytesRecvPerSecond
// update netIoStats
a.netIoStats.BytesSent = totalBytesSent
a.netIoStats.BytesRecv = totalBytesRecv
}
}
}
func (a *Agent) initializeNetIoStats() { func (a *Agent) initializeNetIoStats() {
// reset valid network interfaces // reset valid network interfaces
a.netInterfaces = make(map[string]struct{}, 0) a.netInterfaces = make(map[string]struct{}, 0)

View File

@@ -11,6 +11,7 @@ import (
"github.com/henrygd/beszel" "github.com/henrygd/beszel"
"github.com/henrygd/beszel/agent/battery" "github.com/henrygd/beszel/agent/battery"
"github.com/henrygd/beszel/agent/deltatracker"
"github.com/henrygd/beszel/internal/entities/system" "github.com/henrygd/beszel/internal/entities/system"
"github.com/shirou/gopsutil/v4/cpu" "github.com/shirou/gopsutil/v4/cpu"
@@ -18,9 +19,10 @@ import (
"github.com/shirou/gopsutil/v4/host" "github.com/shirou/gopsutil/v4/host"
"github.com/shirou/gopsutil/v4/load" "github.com/shirou/gopsutil/v4/load"
"github.com/shirou/gopsutil/v4/mem" "github.com/shirou/gopsutil/v4/mem"
psutilNet "github.com/shirou/gopsutil/v4/net"
) )
var netInterfaceDeltaTracker = deltatracker.NewDeltaTracker[string, uint64]()
// Sets initial / non-changing values about the host system // Sets initial / non-changing values about the host system
func (a *Agent) initializeSystemInfo() { func (a *Agent) initializeSystemInfo() {
a.systemInfo.AgentVersion = beszel.Version a.systemInfo.AgentVersion = beszel.Version
@@ -70,7 +72,7 @@ func (a *Agent) initializeSystemInfo() {
// Returns current info, stats about the host system // Returns current info, stats about the host system
func (a *Agent) getSystemStats() system.Stats { func (a *Agent) getSystemStats() system.Stats {
systemStats := system.Stats{} var systemStats system.Stats
// battery // battery
if battery.HasReadableBattery() { if battery.HasReadableBattery() {
@@ -173,55 +175,7 @@ func (a *Agent) getSystemStats() system.Stats {
} }
// network stats // network stats
if len(a.netInterfaces) == 0 { a.updateNetworkStats(&systemStats)
// if no network interfaces, initialize again
// this is a fix if agent started before network is online (#466)
// maybe refactor this in the future to not cache interface names at all so we
// don't miss an interface that's been added after agent started in any circumstance
a.initializeNetIoStats()
}
if netIO, err := psutilNet.IOCounters(true); err == nil {
msElapsed := uint64(time.Since(a.netIoStats.Time).Milliseconds())
a.netIoStats.Time = time.Now()
totalBytesSent := uint64(0)
totalBytesRecv := uint64(0)
// sum all bytes sent and received
for _, v := range netIO {
// skip if not in valid network interfaces list
if _, exists := a.netInterfaces[v.Name]; !exists {
continue
}
totalBytesSent += v.BytesSent
totalBytesRecv += v.BytesRecv
}
// add to systemStats
var bytesSentPerSecond, bytesRecvPerSecond uint64
if msElapsed > 0 {
bytesSentPerSecond = (totalBytesSent - a.netIoStats.BytesSent) * 1000 / msElapsed
bytesRecvPerSecond = (totalBytesRecv - a.netIoStats.BytesRecv) * 1000 / msElapsed
}
networkSentPs := bytesToMegabytes(float64(bytesSentPerSecond))
networkRecvPs := bytesToMegabytes(float64(bytesRecvPerSecond))
// add check for issue (#150) where sent is a massive number
if networkSentPs > 10_000 || networkRecvPs > 10_000 {
slog.Warn("Invalid net stats. Resetting.", "sent", networkSentPs, "recv", networkRecvPs)
for _, v := range netIO {
if _, exists := a.netInterfaces[v.Name]; !exists {
continue
}
slog.Info(v.Name, "recv", v.BytesRecv, "sent", v.BytesSent)
}
// reset network I/O stats
a.initializeNetIoStats()
} else {
systemStats.NetworkSent = networkSentPs
systemStats.NetworkRecv = networkRecvPs
systemStats.Bandwidth[0], systemStats.Bandwidth[1] = bytesSentPerSecond, bytesRecvPerSecond
// update netIoStats
a.netIoStats.BytesSent = totalBytesSent
a.netIoStats.BytesRecv = totalBytesRecv
}
}
// temperatures // temperatures
// TODO: maybe refactor to methods on systemStats // TODO: maybe refactor to methods on systemStats

View File

@@ -6,7 +6,7 @@ import "github.com/blang/semver"
const ( const (
// Version is the current version of the application. // Version is the current version of the application.
Version = "0.12.7" Version = "0.12.9"
// AppName is the name of the application. // AppName is the name of the application.
AppName = "beszel" AppName = "beszel"
) )

View File

@@ -25,7 +25,12 @@ type alertInfo struct {
// startWorker is a long-running goroutine that processes alert tasks // startWorker is a long-running goroutine that processes alert tasks
// every x seconds. It must be running to process status alerts. // every x seconds. It must be running to process status alerts.
func (am *AlertManager) startWorker() { func (am *AlertManager) startWorker() {
tick := time.Tick(15 * time.Second) processPendingAlerts := time.Tick(15 * time.Second)
// check for status alerts that are not resolved when system comes up
// (can be removed if we figure out core bug in #1052)
checkStatusAlerts := time.Tick(561 * time.Second)
for { for {
select { select {
case <-am.stopChan: case <-am.stopChan:
@@ -41,7 +46,9 @@ func (am *AlertManager) startWorker() {
case "cancel": case "cancel":
am.pendingAlerts.Delete(task.alertRecord.Id) am.pendingAlerts.Delete(task.alertRecord.Id)
} }
case <-tick: case <-checkStatusAlerts:
resolveStatusAlerts(am.hub)
case <-processPendingAlerts:
// Check for expired alerts every tick // Check for expired alerts every tick
now := time.Now() now := time.Now()
for key, value := range am.pendingAlerts.Range { for key, value := range am.pendingAlerts.Range {
@@ -170,3 +177,35 @@ func (am *AlertManager) sendStatusAlert(alertStatus string, systemName string, a
LinkText: "View " + systemName, LinkText: "View " + systemName,
}) })
} }
// resolveStatusAlerts resolves any status alerts that weren't resolved
// when system came up (https://github.com/henrygd/beszel/issues/1052)
func resolveStatusAlerts(app core.App) error {
db := app.DB()
// Find all active status alerts where the system is actually up
var alertIds []string
err := db.NewQuery(`
SELECT a.id
FROM alerts a
JOIN systems s ON a.system = s.id
WHERE a.name = 'Status'
AND a.triggered = true
AND s.status = 'up'
`).Column(&alertIds)
if err != nil {
return err
}
// resolve all matching alert records
for _, alertId := range alertIds {
alert, err := app.FindRecordById("alerts", alertId)
if err != nil {
return err
}
alert.Set("triggered", false)
err = app.Save(alert)
if err != nil {
return err
}
}
return nil
}

View File

@@ -13,6 +13,7 @@ import (
"testing/synctest" "testing/synctest"
"time" "time"
"github.com/henrygd/beszel/internal/alerts"
beszelTests "github.com/henrygd/beszel/internal/tests" beszelTests "github.com/henrygd/beszel/internal/tests"
"github.com/pocketbase/dbx" "github.com/pocketbase/dbx"
@@ -369,33 +370,9 @@ func TestUserAlertsApi(t *testing.T) {
} }
} }
func getHubWithUser(t *testing.T) (*beszelTests.TestHub, *core.Record) {
hub, err := beszelTests.NewTestHub(t.TempDir())
assert.NoError(t, err)
hub.StartHub()
// Manually initialize the system manager to bind event hooks
err = hub.GetSystemManager().Initialize()
assert.NoError(t, err)
// Create a test user
user, err := beszelTests.CreateUser(hub, "test@example.com", "password")
assert.NoError(t, err)
// Create user settings for the test user (required for alert notifications)
userSettingsData := map[string]any{
"user": user.Id,
"settings": `{"emails":[test@example.com],"webhooks":[]}`,
}
_, err = beszelTests.CreateRecord(hub, "user_settings", userSettingsData)
assert.NoError(t, err)
return hub, user
}
func TestStatusAlerts(t *testing.T) { func TestStatusAlerts(t *testing.T) {
synctest.Test(t, func(t *testing.T) { synctest.Test(t, func(t *testing.T) {
hub, user := getHubWithUser(t) hub, user := beszelTests.GetHubWithUser(t)
defer hub.Cleanup() defer hub.Cleanup()
systems, err := beszelTests.CreateSystems(hub, 4, user.Id, "paused") systems, err := beszelTests.CreateSystems(hub, 4, user.Id, "paused")
@@ -476,7 +453,7 @@ func TestStatusAlerts(t *testing.T) {
func TestAlertsHistory(t *testing.T) { func TestAlertsHistory(t *testing.T) {
synctest.Test(t, func(t *testing.T) { synctest.Test(t, func(t *testing.T) {
hub, user := getHubWithUser(t) hub, user := beszelTests.GetHubWithUser(t)
defer hub.Cleanup() defer hub.Cleanup()
// Create systems and alerts // Create systems and alerts
@@ -602,3 +579,102 @@ func TestAlertsHistory(t *testing.T) {
assert.EqualValues(t, 2, totalHistoryCount, "Should have 2 total alert history records") assert.EqualValues(t, 2, totalHistoryCount, "Should have 2 total alert history records")
}) })
} }
func TestResolveStatusAlerts(t *testing.T) {
hub, user := beszelTests.GetHubWithUser(t)
defer hub.Cleanup()
// Create a systemUp
systemUp, err := beszelTests.CreateRecord(hub, "systems", map[string]any{
"name": "test-system",
"users": []string{user.Id},
"host": "127.0.0.1",
"status": "up",
})
assert.NoError(t, err)
systemDown, err := beszelTests.CreateRecord(hub, "systems", map[string]any{
"name": "test-system-2",
"users": []string{user.Id},
"host": "127.0.0.2",
"status": "up",
})
assert.NoError(t, err)
// Create a status alertUp for the system
alertUp, err := beszelTests.CreateRecord(hub, "alerts", map[string]any{
"name": "Status",
"system": systemUp.Id,
"user": user.Id,
"min": 1,
})
assert.NoError(t, err)
alertDown, err := beszelTests.CreateRecord(hub, "alerts", map[string]any{
"name": "Status",
"system": systemDown.Id,
"user": user.Id,
"min": 1,
})
assert.NoError(t, err)
// Verify alert is not triggered initially
assert.False(t, alertUp.GetBool("triggered"), "Alert should not be triggered initially")
// Set the system to 'up' (this should not trigger the alert)
systemUp.Set("status", "up")
err = hub.SaveNoValidate(systemUp)
assert.NoError(t, err)
systemDown.Set("status", "down")
err = hub.SaveNoValidate(systemDown)
assert.NoError(t, err)
// Wait a moment for any processing
time.Sleep(10 * time.Millisecond)
// Verify alertUp is still not triggered after setting system to up
alertUp, err = hub.FindFirstRecordByFilter("alerts", "id={:id}", dbx.Params{"id": alertUp.Id})
assert.NoError(t, err)
assert.False(t, alertUp.GetBool("triggered"), "Alert should not be triggered when system is up")
// Manually set both alerts triggered to true
alertUp.Set("triggered", true)
err = hub.SaveNoValidate(alertUp)
assert.NoError(t, err)
alertDown.Set("triggered", true)
err = hub.SaveNoValidate(alertDown)
assert.NoError(t, err)
// Verify we have exactly one alert with triggered true
triggeredCount, err := hub.CountRecords("alerts", dbx.HashExp{"triggered": true})
assert.NoError(t, err)
assert.EqualValues(t, 2, triggeredCount, "Should have exactly two alerts with triggered true")
// Verify the specific alertUp is triggered
alertUp, err = hub.FindFirstRecordByFilter("alerts", "id={:id}", dbx.Params{"id": alertUp.Id})
assert.NoError(t, err)
assert.True(t, alertUp.GetBool("triggered"), "Alert should be triggered")
// Verify we have two unresolved alert history records
alertHistoryCount, err := hub.CountRecords("alerts_history", dbx.HashExp{"resolved": ""})
assert.NoError(t, err)
assert.EqualValues(t, 2, alertHistoryCount, "Should have exactly two unresolved alert history records")
err = alerts.ResolveStatusAlerts(hub)
assert.NoError(t, err)
// Verify alertUp is not triggered after resolving
alertUp, err = hub.FindFirstRecordByFilter("alerts", "id={:id}", dbx.Params{"id": alertUp.Id})
assert.NoError(t, err)
assert.False(t, alertUp.GetBool("triggered"), "Alert should not be triggered after resolving")
// Verify alertDown is still triggered
alertDown, err = hub.FindFirstRecordByFilter("alerts", "id={:id}", dbx.Params{"id": alertDown.Id})
assert.NoError(t, err)
assert.True(t, alertDown.GetBool("triggered"), "Alert should still be triggered after resolving")
// Verify we have one unresolved alert history record
alertHistoryCount, err = hub.CountRecords("alerts_history", dbx.HashExp{"resolved": ""})
assert.NoError(t, err)
assert.EqualValues(t, 1, alertHistoryCount, "Should have exactly one unresolved alert history record")
}

View File

@@ -1,3 +1,6 @@
//go:build testing
// +build testing
package alerts package alerts
import ( import (
@@ -53,3 +56,7 @@ func (am *AlertManager) ForceExpirePendingAlerts() {
return true return true
}) })
} }
func ResolveStatusAlerts(app core.App) error {
return resolveStatusAlerts(app)
}

View File

@@ -2,15 +2,18 @@ FROM --platform=$BUILDPLATFORM golang:alpine AS builder
WORKDIR /app WORKDIR /app
COPY go.mod go.sum ./
# RUN go mod download COPY ../go.mod ../go.sum ./
COPY *.go ./ RUN go mod download
COPY cmd ./cmd
COPY internal ./internal # Copy source files
COPY . ./
# Build # Build
ARG TARGETOS TARGETARCH ARG TARGETOS TARGETARCH
RUN CGO_ENABLED=0 GOGC=75 GOOS=$TARGETOS GOARCH=$TARGETARCH go build -ldflags "-w -s" -o /agent ./cmd/agent RUN CGO_ENABLED=0 GOGC=75 GOOS=$TARGETOS GOARCH=$TARGETARCH go build -ldflags "-w -s" -o /agent ./internal/cmd/agent
RUN rm -rf /tmp/*
# -------------------------- # --------------------------
# Final image: GPU-enabled agent with nvidia-smi # Final image: GPU-enabled agent with nvidia-smi
@@ -18,4 +21,7 @@ RUN CGO_ENABLED=0 GOGC=75 GOOS=$TARGETOS GOARCH=$TARGETARCH go build -ldflags "-
FROM nvidia/cuda:12.2.2-base-ubuntu22.04 FROM nvidia/cuda:12.2.2-base-ubuntu22.04
COPY --from=builder /agent /agent COPY --from=builder /agent /agent
# this is so we don't need to create the /tmp directory in the scratch container
COPY --from=builder /tmp /tmp
ENTRYPOINT ["/agent"] ENTRYPOINT ["/agent"]

View File

@@ -38,9 +38,10 @@ type Stats struct {
Bandwidth [2]uint64 `json:"b,omitzero" cbor:"26,keyasint,omitzero"` // [sent bytes, recv bytes] Bandwidth [2]uint64 `json:"b,omitzero" cbor:"26,keyasint,omitzero"` // [sent bytes, recv bytes]
MaxBandwidth [2]uint64 `json:"bm,omitzero" cbor:"27,keyasint,omitzero"` // [sent bytes, recv bytes] MaxBandwidth [2]uint64 `json:"bm,omitzero" cbor:"27,keyasint,omitzero"` // [sent bytes, recv bytes]
// TODO: remove other load fields in future release in favor of load avg array // TODO: remove other load fields in future release in favor of load avg array
LoadAvg [3]float64 `json:"la,omitempty" cbor:"28,keyasint"` LoadAvg [3]float64 `json:"la,omitempty" cbor:"28,keyasint"`
Battery [2]uint8 `json:"bat,omitzero" cbor:"29,keyasint,omitzero"` // [percent, charge state, current] Battery [2]uint8 `json:"bat,omitzero" cbor:"29,keyasint,omitzero"` // [percent, charge state, current]
MaxMem float64 `json:"mm,omitempty" cbor:"30,keyasint,omitempty"` MaxMem float64 `json:"mm,omitempty" cbor:"30,keyasint,omitempty"`
NetworkInterfaces map[string][4]uint64 `json:"ni,omitempty" cbor:"31,keyasint,omitempty"` // [upload bytes, download bytes, total upload, total download]
} }
type GPUData struct { type GPUData struct {

View File

@@ -225,6 +225,19 @@ func (rm *RecordManager) AverageSystemStats(db dbx.Builder, records RecordIds) *
sum.MaxBandwidth[0] = max(sum.MaxBandwidth[0], stats.MaxBandwidth[0], stats.Bandwidth[0]) sum.MaxBandwidth[0] = max(sum.MaxBandwidth[0], stats.MaxBandwidth[0], stats.Bandwidth[0])
sum.MaxBandwidth[1] = max(sum.MaxBandwidth[1], stats.MaxBandwidth[1], stats.Bandwidth[1]) sum.MaxBandwidth[1] = max(sum.MaxBandwidth[1], stats.MaxBandwidth[1], stats.Bandwidth[1])
// Accumulate network interfaces
if sum.NetworkInterfaces == nil {
sum.NetworkInterfaces = make(map[string][4]uint64, len(stats.NetworkInterfaces))
}
for key, value := range stats.NetworkInterfaces {
sum.NetworkInterfaces[key] = [4]uint64{
sum.NetworkInterfaces[key][0] + value[0],
sum.NetworkInterfaces[key][1] + value[1],
max(sum.NetworkInterfaces[key][2], value[2]),
max(sum.NetworkInterfaces[key][3], value[3]),
}
}
// Accumulate temperatures // Accumulate temperatures
if stats.Temperatures != nil { if stats.Temperatures != nil {
if sum.Temperatures == nil { if sum.Temperatures == nil {
@@ -299,6 +312,19 @@ func (rm *RecordManager) AverageSystemStats(db dbx.Builder, records RecordIds) *
sum.Bandwidth[0] = sum.Bandwidth[0] / uint64(count) sum.Bandwidth[0] = sum.Bandwidth[0] / uint64(count)
sum.Bandwidth[1] = sum.Bandwidth[1] / uint64(count) sum.Bandwidth[1] = sum.Bandwidth[1] / uint64(count)
sum.Battery[0] = uint8(batterySum / int(count)) sum.Battery[0] = uint8(batterySum / int(count))
// Average network interfaces
if sum.NetworkInterfaces != nil {
for key := range sum.NetworkInterfaces {
sum.NetworkInterfaces[key] = [4]uint64{
sum.NetworkInterfaces[key][0] / uint64(count),
sum.NetworkInterfaces[key][1] / uint64(count),
sum.NetworkInterfaces[key][2],
sum.NetworkInterfaces[key][3],
}
}
}
// Average temperatures // Average temperatures
if sum.Temperatures != nil && tempCount > 0 { if sum.Temperatures != nil && tempCount > 0 {
for key := range sum.Temperatures { for key := range sum.Temperatures {

View File

@@ -175,7 +175,7 @@ func TestDeleteOldSystemStats(t *testing.T) {
} }
// Run deletion // Run deletion
err = records.TestDeleteOldSystemStats(hub) err = records.DeleteOldSystemStats(hub)
require.NoError(t, err) require.NoError(t, err)
// Verify results // Verify results
@@ -268,7 +268,7 @@ func TestDeleteOldAlertsHistory(t *testing.T) {
assert.Equal(t, int64(tc.alertCount), countBefore, "Initial count should match") assert.Equal(t, int64(tc.alertCount), countBefore, "Initial count should match")
// Run deletion // Run deletion
err = records.TestDeleteOldAlertsHistory(hub, tc.countToKeep, tc.countBeforeDeletion) err = records.DeleteOldAlertsHistory(hub, tc.countToKeep, tc.countBeforeDeletion)
require.NoError(t, err) require.NoError(t, err)
// Count after deletion // Count after deletion
@@ -332,7 +332,7 @@ func TestDeleteOldAlertsHistoryEdgeCases(t *testing.T) {
} }
// Should not error and should not delete anything // Should not error and should not delete anything
err = records.TestDeleteOldAlertsHistory(hub, 10, 20) err = records.DeleteOldAlertsHistory(hub, 10, 20)
require.NoError(t, err) require.NoError(t, err)
count, err := hub.CountRecords("alerts_history") count, err := hub.CountRecords("alerts_history")
@@ -346,7 +346,7 @@ func TestDeleteOldAlertsHistoryEdgeCases(t *testing.T) {
require.NoError(t, err) require.NoError(t, err)
// Should not error with empty table // Should not error with empty table
err = records.TestDeleteOldAlertsHistory(hub, 10, 20) err = records.DeleteOldAlertsHistory(hub, 10, 20)
require.NoError(t, err) require.NoError(t, err)
}) })
} }
@@ -376,7 +376,7 @@ func TestTwoDecimals(t *testing.T) {
} }
for _, tc := range testCases { for _, tc := range testCases {
result := records.TestTwoDecimals(tc.input) result := records.TwoDecimals(tc.input)
assert.InDelta(t, tc.expected, result, 0.02, "twoDecimals(%f) should equal %f", tc.input, tc.expected) assert.InDelta(t, tc.expected, result, 0.02, "twoDecimals(%f) should equal %f", tc.input, tc.expected)
} }
} }

View File

@@ -7,17 +7,17 @@ import (
"github.com/pocketbase/pocketbase/core" "github.com/pocketbase/pocketbase/core"
) )
// TestDeleteOldSystemStats exposes deleteOldSystemStats for testing // DeleteOldSystemStats exposes deleteOldSystemStats for testing
func TestDeleteOldSystemStats(app core.App) error { func DeleteOldSystemStats(app core.App) error {
return deleteOldSystemStats(app) return deleteOldSystemStats(app)
} }
// TestDeleteOldAlertsHistory exposes deleteOldAlertsHistory for testing // DeleteOldAlertsHistory exposes deleteOldAlertsHistory for testing
func TestDeleteOldAlertsHistory(app core.App, countToKeep, countBeforeDeletion int) error { func DeleteOldAlertsHistory(app core.App, countToKeep, countBeforeDeletion int) error {
return deleteOldAlertsHistory(app, countToKeep, countBeforeDeletion) return deleteOldAlertsHistory(app, countToKeep, countBeforeDeletion)
} }
// TestTwoDecimals exposes twoDecimals for testing // TwoDecimals exposes twoDecimals for testing
func TestTwoDecimals(value float64) float64 { func TwoDecimals(value float64) float64 {
return twoDecimals(value) return twoDecimals(value)
} }

View File

@@ -1,12 +1,12 @@
{ {
"name": "beszel", "name": "beszel",
"version": "0.12.7", "version": "0.12.9",
"lockfileVersion": 3, "lockfileVersion": 3,
"requires": true, "requires": true,
"packages": { "packages": {
"": { "": {
"name": "beszel", "name": "beszel",
"version": "0.12.7", "version": "0.12.9",
"dependencies": { "dependencies": {
"@henrygd/queue": "^1.0.7", "@henrygd/queue": "^1.0.7",
"@henrygd/semaphore": "^0.0.2", "@henrygd/semaphore": "^0.0.2",
@@ -46,6 +46,7 @@
"valibot": "^0.42.1" "valibot": "^0.42.1"
}, },
"devDependencies": { "devDependencies": {
"@biomejs/biome": "2.2.3",
"@lingui/cli": "^5.4.1", "@lingui/cli": "^5.4.1",
"@lingui/swc-plugin": "^5.6.1", "@lingui/swc-plugin": "^5.6.1",
"@lingui/vite-plugin": "^5.4.1", "@lingui/vite-plugin": "^5.4.1",
@@ -330,6 +331,169 @@
"node": ">=6.9.0" "node": ">=6.9.0"
} }
}, },
"node_modules/@biomejs/biome": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/biome/-/biome-2.2.3.tgz",
"integrity": "sha512-9w0uMTvPrIdvUrxazZ42Ib7t8Y2yoGLKLdNne93RLICmaHw7mcLv4PPb5LvZLJF3141gQHiCColOh/v6VWlWmg==",
"dev": true,
"license": "MIT OR Apache-2.0",
"bin": {
"biome": "bin/biome"
},
"engines": {
"node": ">=14.21.3"
},
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/biome"
},
"optionalDependencies": {
"@biomejs/cli-darwin-arm64": "2.2.3",
"@biomejs/cli-darwin-x64": "2.2.3",
"@biomejs/cli-linux-arm64": "2.2.3",
"@biomejs/cli-linux-arm64-musl": "2.2.3",
"@biomejs/cli-linux-x64": "2.2.3",
"@biomejs/cli-linux-x64-musl": "2.2.3",
"@biomejs/cli-win32-arm64": "2.2.3",
"@biomejs/cli-win32-x64": "2.2.3"
}
},
"node_modules/@biomejs/cli-darwin-arm64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-arm64/-/cli-darwin-arm64-2.2.3.tgz",
"integrity": "sha512-OrqQVBpadB5eqzinXN4+Q6honBz+tTlKVCsbEuEpljK8ASSItzIRZUA02mTikl3H/1nO2BMPFiJ0nkEZNy3B1w==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-darwin-x64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-darwin-x64/-/cli-darwin-x64-2.2.3.tgz",
"integrity": "sha512-OCdBpb1TmyfsTgBAM1kPMXyYKTohQ48WpiN9tkt9xvU6gKVKHY4oVwteBebiOqyfyzCNaSiuKIPjmHjUZ2ZNMg==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"darwin"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-linux-arm64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64/-/cli-linux-arm64-2.2.3.tgz",
"integrity": "sha512-g/Uta2DqYpECxG+vUmTAmUKlVhnGEcY7DXWgKP8ruLRa8Si1QHsWknPY3B/wCo0KgYiFIOAZ9hjsHfNb9L85+g==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-linux-arm64-musl": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.2.3.tgz",
"integrity": "sha512-q3w9jJ6JFPZPeqyvwwPeaiS/6NEszZ+pXKF+IczNo8Xj6fsii45a4gEEicKyKIytalV+s829ACZujQlXAiVLBQ==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-linux-x64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64/-/cli-linux-x64-2.2.3.tgz",
"integrity": "sha512-LEtyYL1fJsvw35CxrbQ0gZoxOG3oZsAjzfRdvRBRHxOpQ91Q5doRVjvWW/wepgSdgk5hlaNzfeqpyGmfSD0Eyw==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-linux-x64-musl": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-linux-x64-musl/-/cli-linux-x64-musl-2.2.3.tgz",
"integrity": "sha512-y76Dn4vkP1sMRGPFlNc+OTETBhGPJ90jY3il6jAfur8XWrYBQV3swZ1Jo0R2g+JpOeeoA0cOwM7mJG6svDz79w==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"linux"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-win32-arm64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-arm64/-/cli-win32-arm64-2.2.3.tgz",
"integrity": "sha512-Ms9zFYzjcJK7LV+AOMYnjN3pV3xL8Prxf9aWdDVL74onLn5kcvZ1ZMQswE5XHtnd/r/0bnUd928Rpbs14BzVmA==",
"cpu": [
"arm64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@biomejs/cli-win32-x64": {
"version": "2.2.3",
"resolved": "https://registry.npmjs.org/@biomejs/cli-win32-x64/-/cli-win32-x64-2.2.3.tgz",
"integrity": "sha512-gvCpewE7mBwBIpqk1YrUqNR4mCiyJm6UI3YWQQXkedSSEwzRdodRpaKhbdbHw1/hmTWOVXQ+Eih5Qctf4TCVOQ==",
"cpu": [
"x64"
],
"dev": true,
"license": "MIT OR Apache-2.0",
"optional": true,
"os": [
"win32"
],
"engines": {
"node": ">=14.21.3"
}
},
"node_modules/@esbuild/aix-ppc64": { "node_modules/@esbuild/aix-ppc64": {
"version": "0.25.6", "version": "0.25.6",
"resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.25.6.tgz", "resolved": "https://registry.npmjs.org/@esbuild/aix-ppc64/-/aix-ppc64-0.25.6.tgz",
@@ -5763,14 +5927,14 @@
"license": "MIT" "license": "MIT"
}, },
"node_modules/tinyglobby": { "node_modules/tinyglobby": {
"version": "0.2.14", "version": "0.2.15",
"resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.14.tgz", "resolved": "https://registry.npmjs.org/tinyglobby/-/tinyglobby-0.2.15.tgz",
"integrity": "sha512-tX5e7OM1HnYr2+a2C/4V0htOcSQcoSTH9KgJnVvNm5zm/cyEWKJ7j7YutsH9CxMdtOkkLFy2AHrMci9IM8IPZQ==", "integrity": "sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==",
"dev": true, "dev": true,
"license": "MIT", "license": "MIT",
"dependencies": { "dependencies": {
"fdir": "^6.4.4", "fdir": "^6.5.0",
"picomatch": "^4.0.2" "picomatch": "^4.0.3"
}, },
"engines": { "engines": {
"node": ">=12.0.0" "node": ">=12.0.0"
@@ -5957,9 +6121,9 @@
} }
}, },
"node_modules/vite": { "node_modules/vite": {
"version": "7.1.3", "version": "7.1.5",
"resolved": "https://registry.npmjs.org/vite/-/vite-7.1.3.tgz", "resolved": "https://registry.npmjs.org/vite/-/vite-7.1.5.tgz",
"integrity": "sha512-OOUi5zjkDxYrKhTV3V7iKsoS37VUM7v40+HuwEmcrsf11Cdx9y3DIr2Px6liIcZFwt3XSRpQvFpL3WVy7ApkGw==", "integrity": "sha512-4cKBO9wR75r0BeIWWWId9XK9Lj6La5X846Zw9dFfzMRw38IlTk2iCcUt6hsyiDRcPidc55ZParFYDXi0nXOeLQ==",
"dev": true, "dev": true,
"license": "MIT", "license": "MIT",
"dependencies": { "dependencies": {
@@ -5968,7 +6132,7 @@
"picomatch": "^4.0.3", "picomatch": "^4.0.3",
"postcss": "^8.5.6", "postcss": "^8.5.6",
"rollup": "^4.43.0", "rollup": "^4.43.0",
"tinyglobby": "^0.2.14" "tinyglobby": "^0.2.15"
}, },
"bin": { "bin": {
"vite": "bin/vite.js" "vite": "bin/vite.js"

View File

@@ -1,7 +1,7 @@
{ {
"name": "beszel", "name": "beszel",
"private": true, "private": true,
"version": "0.12.7", "version": "0.12.9",
"type": "module", "type": "module",
"scripts": { "scripts": {
"dev": "vite --host", "dev": "vite --host",
@@ -76,4 +76,4 @@
"optionalDependencies": { "optionalDependencies": {
"@esbuild/linux-arm64": "^0.21.5" "@esbuild/linux-arm64": "^0.21.5"
} }
} }

View File

@@ -1,5 +1,9 @@
import { Trans } from "@lingui/react/macro"
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { Trans } from "@lingui/react/macro"
import { useStore } from "@nanostores/react"
import { getPagePath } from "@nanostores/router"
import { ChevronDownIcon, ExternalLinkIcon, PlusIcon } from "lucide-react"
import { memo, useEffect, useRef, useState } from "react"
import { Button } from "@/components/ui/button" import { Button } from "@/components/ui/button"
import { import {
Dialog, Dialog,
@@ -10,34 +14,30 @@ import {
DialogTitle, DialogTitle,
DialogTrigger, DialogTrigger,
} from "@/components/ui/dialog" } from "@/components/ui/dialog"
import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs"
import { Input } from "@/components/ui/input" import { Input } from "@/components/ui/input"
import { Label } from "@/components/ui/label" import { Label } from "@/components/ui/label"
import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs"
import { isReadOnlyUser, pb } from "@/lib/api"
import { SystemStatus } from "@/lib/enums"
import { $publicKey } from "@/lib/stores" import { $publicKey } from "@/lib/stores"
import { cn, generateToken, tokenMap, useBrowserStorage } from "@/lib/utils" import { cn, generateToken, tokenMap, useBrowserStorage } from "@/lib/utils"
import { pb, isReadOnlyUser } from "@/lib/api" import type { SystemRecord } from "@/types"
import { useStore } from "@nanostores/react"
import { ChevronDownIcon, ExternalLinkIcon, PlusIcon } from "lucide-react"
import { memo, useEffect, useRef, useState } from "react"
import { $router, basePath, Link, navigate } from "./router"
import { SystemRecord } from "@/types"
import { SystemStatus } from "@/lib/enums"
import { AppleIcon, DockerIcon, FreeBsdIcon, TuxIcon, WindowsIcon } from "./ui/icons"
import { InputCopy } from "./ui/input-copy"
import { getPagePath } from "@nanostores/router"
import { import {
copyDockerCompose, copyDockerCompose,
copyDockerRun, copyDockerRun,
copyLinuxCommand, copyLinuxCommand,
copyWindowsCommand, copyWindowsCommand,
DropdownItem, type DropdownItem,
InstallDropdown, InstallDropdown,
} from "./install-dropdowns" } from "./install-dropdowns"
import { $router, basePath, Link, navigate } from "./router"
import { DropdownMenu, DropdownMenuTrigger } from "./ui/dropdown-menu" import { DropdownMenu, DropdownMenuTrigger } from "./ui/dropdown-menu"
import { AppleIcon, DockerIcon, FreeBsdIcon, TuxIcon, WindowsIcon } from "./ui/icons"
import { InputCopy } from "./ui/input-copy"
export function AddSystemButton({ className }: { className?: string }) { export function AddSystemButton({ className }: { className?: string }) {
const [open, setOpen] = useState(false) const [open, setOpen] = useState(false)
let opened = useRef(false) const opened = useRef(false)
if (open) { if (open) {
opened.current = true opened.current = true
} }

View File

@@ -1,11 +1,11 @@
import { ColumnDef } from "@tanstack/react-table"
import { AlertsHistoryRecord } from "@/types"
import { Button } from "@/components/ui/button"
import { Badge } from "@/components/ui/badge"
import { formatShortDate, toFixedFloat, formatDuration, cn } from "@/lib/utils"
import { alertInfo } from "@/lib/alerts"
import { Trans } from "@lingui/react/macro"
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { Trans } from "@lingui/react/macro"
import type { ColumnDef } from "@tanstack/react-table"
import { Badge } from "@/components/ui/badge"
import { Button } from "@/components/ui/button"
import { alertInfo } from "@/lib/alerts"
import { cn, formatDuration, formatShortDate, toFixedFloat } from "@/lib/utils"
import type { AlertsHistoryRecord } from "@/types"
export const alertsHistoryColumns: ColumnDef<AlertsHistoryRecord>[] = [ export const alertsHistoryColumns: ColumnDef<AlertsHistoryRecord>[] = [
{ {
@@ -38,7 +38,7 @@ export const alertsHistoryColumns: ColumnDef<AlertsHistoryRecord>[] = [
</Button> </Button>
), ),
cell: ({ getValue, row }) => { cell: ({ getValue, row }) => {
let name = getValue() as string const name = getValue() as string
const info = alertInfo[row.original.name] const info = alertInfo[row.original.name]
const Icon = info?.icon const Icon = info?.icon

View File

@@ -1,13 +1,13 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { memo, useMemo, useState } from "react"
import { useStore } from "@nanostores/react" import { useStore } from "@nanostores/react"
import { $alerts } from "@/lib/stores"
import { BellIcon } from "lucide-react" import { BellIcon } from "lucide-react"
import { cn } from "@/lib/utils" import { memo, useMemo, useState } from "react"
import { Button } from "@/components/ui/button" import { Button } from "@/components/ui/button"
import { SystemRecord } from "@/types"
import { AlertDialogContent } from "./alerts-sheet"
import { Sheet, SheetContent, SheetTrigger } from "@/components/ui/sheet" import { Sheet, SheetContent, SheetTrigger } from "@/components/ui/sheet"
import { $alerts } from "@/lib/stores"
import { cn } from "@/lib/utils"
import type { SystemRecord } from "@/types"
import { AlertDialogContent } from "./alerts-sheet"
export default memo(function AlertsButton({ system }: { system: SystemRecord }) { export default memo(function AlertsButton({ system }: { system: SystemRecord }) {
const [opened, setOpened] = useState(false) const [opened, setOpened] = useState(false)

View File

@@ -1,21 +1,20 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { Trans, Plural } from "@lingui/react/macro" import { Plural, Trans } from "@lingui/react/macro"
import { $alerts, $systems } from "@/lib/stores"
import { cn, debounce } from "@/lib/utils"
import { alertInfo } from "@/lib/alerts"
import { Switch } from "@/components/ui/switch"
import { AlertInfo, AlertRecord, SystemRecord } from "@/types"
import { lazy, memo, Suspense, useMemo, useState } from "react"
import { toast } from "@/components/ui/use-toast"
import { useStore } from "@nanostores/react" import { useStore } from "@nanostores/react"
import { getPagePath } from "@nanostores/router" import { getPagePath } from "@nanostores/router"
import { Checkbox } from "@/components/ui/checkbox" import { GlobeIcon, ServerIcon } from "lucide-react"
import { DialogTitle, DialogDescription } from "@/components/ui/dialog" import { lazy, memo, Suspense, useMemo, useState } from "react"
import { Tabs, TabsList, TabsTrigger, TabsContent } from "@/components/ui/tabs"
import { ServerIcon, GlobeIcon } from "lucide-react"
import { $router, Link } from "@/components/router" import { $router, Link } from "@/components/router"
import { DialogHeader } from "@/components/ui/dialog" import { Checkbox } from "@/components/ui/checkbox"
import { DialogDescription, DialogHeader, DialogTitle } from "@/components/ui/dialog"
import { Switch } from "@/components/ui/switch"
import { Tabs, TabsContent, TabsList, TabsTrigger } from "@/components/ui/tabs"
import { toast } from "@/components/ui/use-toast"
import { alertInfo } from "@/lib/alerts"
import { pb } from "@/lib/api" import { pb } from "@/lib/api"
import { $alerts, $systems } from "@/lib/stores"
import { cn, debounce } from "@/lib/utils"
import type { AlertInfo, AlertRecord, SystemRecord } from "@/types"
const Slider = lazy(() => import("@/components/ui/slider")) const Slider = lazy(() => import("@/components/ui/slider"))
@@ -172,7 +171,7 @@ export function AlertContent({
const [checked, setChecked] = useState(global ? false : !!alert) const [checked, setChecked] = useState(global ? false : !!alert)
const [min, setMin] = useState(alert?.min || 10) const [min, setMin] = useState(alert?.min || 10)
const [value, setValue] = useState(alert?.value || (singleDescription ? 0 : alertData.start ?? 80)) const [value, setValue] = useState(alert?.value || (singleDescription ? 0 : (alertData.start ?? 80)))
const Icon = alertData.icon const Icon = alertData.icon

View File

@@ -1,9 +1,16 @@
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { cn, formatShortDate, chartMargin } from "@/lib/utils"
import { useYAxisWidth } from "./hooks"
import { ChartData, SystemStatsRecord } from "@/types"
import { useMemo } from "react" import { useMemo } from "react"
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import {
ChartContainer,
ChartLegend,
ChartLegendContent,
ChartTooltip,
ChartTooltipContent,
xAxis,
} from "@/components/ui/chart"
import { chartMargin, cn, formatShortDate } from "@/lib/utils"
import type { ChartData, SystemStatsRecord } from "@/types"
import { useYAxisWidth } from "./hooks"
export type DataPoint = { export type DataPoint = {
label: string label: string
@@ -20,6 +27,8 @@ export default function AreaChartDefault({
contentFormatter, contentFormatter,
dataPoints, dataPoints,
domain, domain,
legend,
itemSorter,
}: // logRender = false, }: // logRender = false,
{ {
chartData: ChartData chartData: ChartData
@@ -29,10 +38,13 @@ export default function AreaChartDefault({
contentFormatter: ({ value, payload }: { value: number; payload: SystemStatsRecord }) => string contentFormatter: ({ value, payload }: { value: number; payload: SystemStatsRecord }) => string
dataPoints?: DataPoint[] dataPoints?: DataPoint[]
domain?: [number, number] domain?: [number, number]
legend?: boolean
itemSorter?: (a: any, b: any) => number
// logRender?: boolean // logRender?: boolean
}) { }) {
const { yAxisWidth, updateYAxisWidth } = useYAxisWidth() const { yAxisWidth, updateYAxisWidth } = useYAxisWidth()
// biome-ignore lint/correctness/useExhaustiveDependencies: ignore
return useMemo(() => { return useMemo(() => {
if (chartData.systemStats.length === 0) { if (chartData.systemStats.length === 0) {
return null return null
@@ -63,6 +75,8 @@ export default function AreaChartDefault({
<ChartTooltip <ChartTooltip
animationEasing="ease-out" animationEasing="ease-out"
animationDuration={150} animationDuration={150}
// @ts-expect-error
itemSorter={itemSorter}
content={ content={
<ChartTooltipContent <ChartTooltipContent
labelFormatter={(_, data) => formatShortDate(data[0].payload.created)} labelFormatter={(_, data) => formatShortDate(data[0].payload.created)}
@@ -70,11 +84,14 @@ export default function AreaChartDefault({
/> />
} }
/> />
{dataPoints?.map((dataPoint, i) => { {dataPoints?.map((dataPoint) => {
const color = `var(--chart-${dataPoint.color})` let { color } = dataPoint
if (typeof color === "number") {
color = `var(--chart-${color})`
}
return ( return (
<Area <Area
key={i} key={dataPoint.label}
dataKey={dataPoint.dataKey} dataKey={dataPoint.dataKey}
name={dataPoint.label} name={dataPoint.label}
type="monotoneX" type="monotoneX"
@@ -85,7 +102,7 @@ export default function AreaChartDefault({
/> />
) )
})} })}
{/* <ChartLegend content={<ChartLegendContent />} /> */} {legend && <ChartLegend content={<ChartLegendContent />} />}
</AreaChart> </AreaChart>
</ChartContainer> </ChartContainer>
</div> </div>

View File

@@ -1,9 +1,9 @@
import { useStore } from "@nanostores/react"
import { HistoryIcon } from "lucide-react"
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select" import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select"
import { $chartTime } from "@/lib/stores" import { $chartTime } from "@/lib/stores"
import { chartTimeData, cn } from "@/lib/utils" import { chartTimeData, cn } from "@/lib/utils"
import { ChartTimes } from "@/types" import type { ChartTimes } from "@/types"
import { useStore } from "@nanostores/react"
import { HistoryIcon } from "lucide-react"
export default function ChartTimeSelect({ className }: { className?: string }) { export default function ChartTimeSelect({ className }: { className?: string }) {
const chartTime = useStore($chartTime) const chartTime = useStore($chartTime)

View File

@@ -1,13 +1,13 @@
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { type ChartConfig, ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { memo, useMemo } from "react"
import { cn, formatShortDate, chartMargin, toFixedFloat, formatBytes, decimalString } from "@/lib/utils"
// import Spinner from '../spinner' // import Spinner from '../spinner'
import { useStore } from "@nanostores/react" import { useStore } from "@nanostores/react"
import { memo, useMemo } from "react"
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { type ChartConfig, ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { ChartType, Unit } from "@/lib/enums"
import { $containerFilter, $userSettings } from "@/lib/stores" import { $containerFilter, $userSettings } from "@/lib/stores"
import { chartMargin, cn, decimalString, formatBytes, formatShortDate, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types" import type { ChartData } from "@/types"
import { Separator } from "../ui/separator" import { Separator } from "../ui/separator"
import { ChartType, Unit } from "@/lib/enums"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function ContainerChart({ export default memo(function ContainerChart({

View File

@@ -1,10 +1,10 @@
import { useLingui } from "@lingui/react/macro"
import { memo } from "react"
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts" import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart" import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { cn, formatShortDate, decimalString, chartMargin, formatBytes, toFixedFloat } from "@/lib/utils"
import { ChartData } from "@/types"
import { memo } from "react"
import { useLingui } from "@lingui/react/macro"
import { Unit } from "@/lib/enums" import { Unit } from "@/lib/enums"
import { chartMargin, cn, decimalString, formatBytes, formatShortDate, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function DiskChart({ export default memo(function DiskChart({

View File

@@ -1,5 +1,5 @@
import { memo, useMemo } from "react"
import { CartesianGrid, Line, LineChart, YAxis } from "recharts" import { CartesianGrid, Line, LineChart, YAxis } from "recharts"
import { import {
ChartContainer, ChartContainer,
ChartLegend, ChartLegend,
@@ -8,9 +8,8 @@ import {
ChartTooltipContent, ChartTooltipContent,
xAxis, xAxis,
} from "@/components/ui/chart" } from "@/components/ui/chart"
import { cn, formatShortDate, toFixedFloat, decimalString, chartMargin } from "@/lib/utils" import { chartMargin, cn, decimalString, formatShortDate, toFixedFloat } from "@/lib/utils"
import { ChartData } from "@/types" import type { ChartData } from "@/types"
import { memo, useMemo } from "react"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData }) { export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData }) {
@@ -27,10 +26,10 @@ export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData
colors: Record<string, string> colors: Record<string, string>
} }
const powerSums = {} as Record<string, number> const powerSums = {} as Record<string, number>
for (let data of chartData.systemStats) { for (const data of chartData.systemStats) {
let newData = { created: data.created } as Record<string, number | string> const newData = { created: data.created } as Record<string, number | string>
for (let gpu of Object.values(data.stats?.g ?? {})) { for (const gpu of Object.values(data.stats?.g ?? {})) {
if (gpu.p) { if (gpu.p) {
const name = gpu.n const name = gpu.n
newData[name] = gpu.p newData[name] = gpu.p
@@ -40,7 +39,7 @@ export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData
newChartData.data.push(newData) newChartData.data.push(newData)
} }
const keys = Object.keys(powerSums).sort((a, b) => powerSums[b] - powerSums[a]) const keys = Object.keys(powerSums).sort((a, b) => powerSums[b] - powerSums[a])
for (let key of keys) { for (const key of keys) {
newChartData.colors[key] = `hsl(${((keys.indexOf(key) * 360) / keys.length) % 360}, 60%, 55%)` newChartData.colors[key] = `hsl(${((keys.indexOf(key) * 360) / keys.length) % 360}, 60%, 55%)`
} }
return newChartData return newChartData
@@ -67,7 +66,7 @@ export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData
width={yAxisWidth} width={yAxisWidth}
tickFormatter={(value) => { tickFormatter={(value) => {
const val = toFixedFloat(value, 2) const val = toFixedFloat(value, 2)
return updateYAxisWidth(val + "W") return updateYAxisWidth(`${val}W`)
}} }}
tickLine={false} tickLine={false}
axisLine={false} axisLine={false}
@@ -76,12 +75,12 @@ export default memo(function GpuPowerChart({ chartData }: { chartData: ChartData
<ChartTooltip <ChartTooltip
animationEasing="ease-out" animationEasing="ease-out"
animationDuration={150} animationDuration={150}
// @ts-ignore // @ts-expect-error
itemSorter={(a, b) => b.value - a.value} itemSorter={(a, b) => b.value - a.value}
content={ content={
<ChartTooltipContent <ChartTooltipContent
labelFormatter={(_, data) => formatShortDate(data[0].payload.created)} labelFormatter={(_, data) => formatShortDate(data[0].payload.created)}
contentFormatter={(item) => decimalString(item.value) + "W"} contentFormatter={(item) => `${decimalString(item.value)}W`}
// indicator="line" // indicator="line"
/> />
} }

View File

@@ -1,6 +1,6 @@
import { useMemo, useState } from "react" import { useMemo, useState } from "react"
import { ChartConfig } from "@/components/ui/chart" import type { ChartConfig } from "@/components/ui/chart"
import { ChartData } from "@/types" import type { ChartData, SystemStats, SystemStatsRecord } from "@/types"
/** Chart configurations for CPU, memory, and network usage charts */ /** Chart configurations for CPU, memory, and network usage charts */
export interface ContainerChartConfigs { export interface ContainerChartConfigs {
@@ -105,3 +105,21 @@ export function useYAxisWidth() {
} }
return { yAxisWidth, updateYAxisWidth } return { yAxisWidth, updateYAxisWidth }
} }
// Assures consistent colors for network interfaces
export function useNetworkInterfaces(interfaces: SystemStats["ni"]) {
const keys = Object.keys(interfaces ?? {})
const sortedKeys = keys.sort((a, b) => (interfaces?.[b]?.[3] ?? 0) - (interfaces?.[a]?.[3] ?? 0))
return {
length: sortedKeys.length,
data: (index = 3) => {
return sortedKeys.map((key) => ({
label: key,
dataKey: (stats: SystemStatsRecord) => stats.stats?.ni?.[key]?.[index],
color: `hsl(${220 + (((sortedKeys.indexOf(key) * 360) / sortedKeys.length) % 360)}, 70%, 50%)`,
opacity: 0.3,
}))
},
}
}

View File

@@ -0,0 +1,110 @@
import { useMemo } from "react"
import { CartesianGrid, Line, LineChart, YAxis } from "recharts"
import {
ChartContainer,
ChartLegend,
ChartLegendContent,
ChartTooltip,
ChartTooltipContent,
xAxis,
} from "@/components/ui/chart"
import { chartMargin, cn, formatShortDate } from "@/lib/utils"
import type { ChartData, SystemStatsRecord } from "@/types"
import { useYAxisWidth } from "./hooks"
export type DataPoint = {
label: string
dataKey: (data: SystemStatsRecord) => number | undefined
color: number | string
}
export default function LineChartDefault({
chartData,
max,
maxToggled,
tickFormatter,
contentFormatter,
dataPoints,
domain,
legend,
itemSorter,
}: // logRender = false,
{
chartData: ChartData
max?: number
maxToggled?: boolean
tickFormatter: (value: number, index: number) => string
contentFormatter: ({ value, payload }: { value: number; payload: SystemStatsRecord }) => string
dataPoints?: DataPoint[]
domain?: [number, number]
legend?: boolean
itemSorter?: (a: any, b: any) => number
// logRender?: boolean
}) {
const { yAxisWidth, updateYAxisWidth } = useYAxisWidth()
// biome-ignore lint/correctness/useExhaustiveDependencies: ignore
return useMemo(() => {
if (chartData.systemStats.length === 0) {
return null
}
// if (logRender) {
// console.log("Rendered at", new Date())
// }
return (
<div>
<ChartContainer
className={cn("h-full w-full absolute aspect-auto bg-card opacity-0 transition-opacity", {
"opacity-100": yAxisWidth,
})}
>
<LineChart accessibilityLayer data={chartData.systemStats} margin={chartMargin}>
<CartesianGrid vertical={false} />
<YAxis
direction="ltr"
orientation={chartData.orientation}
className="tracking-tighter"
width={yAxisWidth}
domain={domain ?? [0, max ?? "auto"]}
tickFormatter={(value, index) => updateYAxisWidth(tickFormatter(value, index))}
tickLine={false}
axisLine={false}
/>
{xAxis(chartData)}
<ChartTooltip
animationEasing="ease-out"
animationDuration={150}
// @ts-expect-error
itemSorter={itemSorter}
content={
<ChartTooltipContent
labelFormatter={(_, data) => formatShortDate(data[0].payload.created)}
contentFormatter={contentFormatter}
/>
}
/>
{dataPoints?.map((dataPoint) => {
let { color } = dataPoint
if (typeof color === "number") {
color = `var(--chart-${color})`
}
return (
<Line
key={dataPoint.label}
dataKey={dataPoint.dataKey}
name={dataPoint.label}
type="monotoneX"
dot={false}
strokeWidth={1.5}
stroke={color}
isAnimationActive={false}
/>
)
})}
{legend && <ChartLegend content={<ChartLegendContent />} />}
</LineChart>
</ChartContainer>
</div>
)
}, [chartData.systemStats.at(-1), yAxisWidth, maxToggled])
}

View File

@@ -1,5 +1,6 @@
import { t } from "@lingui/core/macro"
import { memo } from "react"
import { CartesianGrid, Line, LineChart, YAxis } from "recharts" import { CartesianGrid, Line, LineChart, YAxis } from "recharts"
import { import {
ChartContainer, ChartContainer,
ChartLegend, ChartLegend,
@@ -8,10 +9,8 @@ import {
ChartTooltipContent, ChartTooltipContent,
xAxis, xAxis,
} from "@/components/ui/chart" } from "@/components/ui/chart"
import { cn, formatShortDate, toFixedFloat, decimalString, chartMargin } from "@/lib/utils" import { chartMargin, cn, decimalString, formatShortDate, toFixedFloat } from "@/lib/utils"
import { ChartData, SystemStats } from "@/types" import type { ChartData, SystemStats } from "@/types"
import { memo } from "react"
import { t } from "@lingui/core/macro"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function LoadAverageChart({ chartData }: { chartData: ChartData }) { export default memo(function LoadAverageChart({ chartData }: { chartData: ChartData }) {
@@ -60,7 +59,7 @@ export default memo(function LoadAverageChart({ chartData }: { chartData: ChartD
<ChartTooltip <ChartTooltip
animationEasing="ease-out" animationEasing="ease-out"
animationDuration={150} animationDuration={150}
// @ts-ignore // @ts-expect-error
// itemSorter={(a, b) => b.value - a.value} // itemSorter={(a, b) => b.value - a.value}
content={ content={
<ChartTooltipContent <ChartTooltipContent

View File

@@ -1,10 +1,10 @@
import { useLingui } from "@lingui/react/macro"
import { memo } from "react"
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts" import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart" import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { cn, decimalString, formatShortDate, chartMargin, formatBytes, toFixedFloat } from "@/lib/utils"
import { memo } from "react"
import { ChartData } from "@/types"
import { useLingui } from "@lingui/react/macro"
import { Unit } from "@/lib/enums" import { Unit } from "@/lib/enums"
import { chartMargin, cn, decimalString, formatBytes, formatShortDate, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function MemChart({ chartData, showMax }: { chartData: ChartData; showMax: boolean }) { export default memo(function MemChart({ chartData, showMax }: { chartData: ChartData; showMax: boolean }) {
@@ -53,7 +53,7 @@ export default memo(function MemChart({ chartData, showMax }: { chartData: Chart
animationDuration={150} animationDuration={150}
content={ content={
<ChartTooltipContent <ChartTooltipContent
// @ts-ignore // @ts-expect-error
itemSorter={(a, b) => a.order - b.order} itemSorter={(a, b) => a.order - b.order}
labelFormatter={(_, data) => formatShortDate(data[0].payload.created)} labelFormatter={(_, data) => formatShortDate(data[0].payload.created)}
contentFormatter={({ value }) => { contentFormatter={({ value }) => {

View File

@@ -1,12 +1,11 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { useStore } from "@nanostores/react"
import { memo } from "react"
import { Area, AreaChart, CartesianGrid, YAxis } from "recharts" import { Area, AreaChart, CartesianGrid, YAxis } from "recharts"
import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart" import { ChartContainer, ChartTooltip, ChartTooltipContent, xAxis } from "@/components/ui/chart"
import { cn, formatShortDate, decimalString, chartMargin, formatBytes, toFixedFloat } from "@/lib/utils"
import { ChartData } from "@/types"
import { memo } from "react"
import { $userSettings } from "@/lib/stores" import { $userSettings } from "@/lib/stores"
import { useStore } from "@nanostores/react" import { chartMargin, cn, decimalString, formatBytes, formatShortDate, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function SwapChart({ chartData }: { chartData: ChartData }) { export default memo(function SwapChart({ chartData }: { chartData: ChartData }) {

View File

@@ -1,5 +1,6 @@
import { useStore } from "@nanostores/react"
import { memo, useMemo } from "react"
import { CartesianGrid, Line, LineChart, YAxis } from "recharts" import { CartesianGrid, Line, LineChart, YAxis } from "recharts"
import { import {
ChartContainer, ChartContainer,
ChartLegend, ChartLegend,
@@ -8,11 +9,9 @@ import {
ChartTooltipContent, ChartTooltipContent,
xAxis, xAxis,
} from "@/components/ui/chart" } from "@/components/ui/chart"
import { cn, formatShortDate, toFixedFloat, chartMargin, formatTemperature, decimalString } from "@/lib/utils"
import { ChartData } from "@/types"
import { memo, useMemo } from "react"
import { $temperatureFilter, $userSettings } from "@/lib/stores" import { $temperatureFilter, $userSettings } from "@/lib/stores"
import { useStore } from "@nanostores/react" import { chartMargin, cn, decimalString, formatShortDate, formatTemperature, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types"
import { useYAxisWidth } from "./hooks" import { useYAxisWidth } from "./hooks"
export default memo(function TemperatureChart({ chartData }: { chartData: ChartData }) { export default memo(function TemperatureChart({ chartData }: { chartData: ChartData }) {
@@ -31,18 +30,18 @@ export default memo(function TemperatureChart({ chartData }: { chartData: ChartD
colors: Record<string, string> colors: Record<string, string>
} }
const tempSums = {} as Record<string, number> const tempSums = {} as Record<string, number>
for (let data of chartData.systemStats) { for (const data of chartData.systemStats) {
let newData = { created: data.created } as Record<string, number | string> const newData = { created: data.created } as Record<string, number | string>
let keys = Object.keys(data.stats?.t ?? {}) const keys = Object.keys(data.stats?.t ?? {})
for (let i = 0; i < keys.length; i++) { for (let i = 0; i < keys.length; i++) {
let key = keys[i] const key = keys[i]
newData[key] = data.stats.t![key] newData[key] = data.stats.t![key]
tempSums[key] = (tempSums[key] ?? 0) + newData[key] tempSums[key] = (tempSums[key] ?? 0) + newData[key]
} }
newChartData.data.push(newData) newChartData.data.push(newData)
} }
const keys = Object.keys(tempSums).sort((a, b) => tempSums[b] - tempSums[a]) const keys = Object.keys(tempSums).sort((a, b) => tempSums[b] - tempSums[a])
for (let key of keys) { for (const key of keys) {
newChartData.colors[key] = `hsl(${((keys.indexOf(key) * 360) / keys.length) % 360}, 60%, 55%)` newChartData.colors[key] = `hsl(${((keys.indexOf(key) * 360) / keys.length) % 360}, 60%, 55%)`
} }
return newChartData return newChartData
@@ -78,7 +77,7 @@ export default memo(function TemperatureChart({ chartData }: { chartData: ChartD
<ChartTooltip <ChartTooltip
animationEasing="ease-out" animationEasing="ease-out"
animationDuration={150} animationDuration={150}
// @ts-ignore // @ts-expect-error
itemSorter={(a, b) => b.value - a.value} itemSorter={(a, b) => b.value - a.value}
content={ content={
<ChartTooltipContent <ChartTooltipContent
@@ -93,7 +92,7 @@ export default memo(function TemperatureChart({ chartData }: { chartData: ChartD
/> />
{colors.map((key) => { {colors.map((key) => {
const filtered = filter && !key.toLowerCase().includes(filter.toLowerCase()) const filtered = filter && !key.toLowerCase().includes(filter.toLowerCase())
let strokeOpacity = filtered ? 0.1 : 1 const strokeOpacity = filtered ? 0.1 : 1
return ( return (
<Line <Line
key={key} key={key}

View File

@@ -1,3 +1,7 @@
import { t } from "@lingui/core/macro"
import { Trans } from "@lingui/react/macro"
import { getPagePath } from "@nanostores/router"
import { DialogDescription } from "@radix-ui/react-dialog"
import { import {
AlertOctagonIcon, AlertOctagonIcon,
BookIcon, BookIcon,
@@ -10,7 +14,7 @@ import {
SettingsIcon, SettingsIcon,
UsersIcon, UsersIcon,
} from "lucide-react" } from "lucide-react"
import { memo, useEffect, useMemo } from "react"
import { import {
CommandDialog, CommandDialog,
CommandEmpty, CommandEmpty,
@@ -21,15 +25,10 @@ import {
CommandSeparator, CommandSeparator,
CommandShortcut, CommandShortcut,
} from "@/components/ui/command" } from "@/components/ui/command"
import { memo, useEffect, useMemo } from "react" import { isAdmin } from "@/lib/api"
import { $systems } from "@/lib/stores" import { $systems } from "@/lib/stores"
import { getHostDisplayValue, listen } from "@/lib/utils" import { getHostDisplayValue, listen } from "@/lib/utils"
import { $router, basePath, navigate, prependBasePath } from "./router" import { $router, basePath, navigate, prependBasePath } from "./router"
import { Trans } from "@lingui/react/macro"
import { t } from "@lingui/core/macro"
import { getPagePath } from "@nanostores/router"
import { DialogDescription } from "@radix-ui/react-dialog"
import { isAdmin } from "@/lib/api"
export default memo(function CommandPalette({ open, setOpen }: { open: boolean; setOpen: (open: boolean) => void }) { export default memo(function CommandPalette({ open, setOpen }: { open: boolean; setOpen: (open: boolean) => void }) {
useEffect(() => { useEffect(() => {

View File

@@ -1,8 +1,8 @@
import { Trans } from "@lingui/react/macro"; import { Trans } from "@lingui/react/macro"
import { useEffect, useMemo, useRef } from "react" import { useEffect, useMemo, useRef } from "react"
import { $copyContent } from "@/lib/stores"
import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from "./ui/dialog" import { Dialog, DialogContent, DialogDescription, DialogHeader, DialogTitle } from "./ui/dialog"
import { Textarea } from "./ui/textarea" import { Textarea } from "./ui/textarea"
import { $copyContent } from "@/lib/stores"
export default function CopyToClipboard({ content }: { content: string }) { export default function CopyToClipboard({ content }: { content: string }) {
return ( return (

View File

@@ -1,7 +1,7 @@
import { memo } from "react"
import { DropdownMenuContent, DropdownMenuItem } from "./ui/dropdown-menu"
import { copyToClipboard, getHubURL } from "@/lib/utils"
import { i18n } from "@lingui/core" import { i18n } from "@lingui/core"
import { memo } from "react"
import { copyToClipboard, getHubURL } from "@/lib/utils"
import { DropdownMenuContent, DropdownMenuItem } from "./ui/dropdown-menu"
// const isbeta = beszel.hub_version.includes("beta") // const isbeta = beszel.hub_version.includes("beta")
// const imagetag = isbeta ? ":edge" : "" // const imagetag = isbeta ? ":edge" : ""

View File

@@ -1,11 +1,10 @@
import { useLingui } from "@lingui/react/macro"
import { LanguagesIcon } from "lucide-react" import { LanguagesIcon } from "lucide-react"
import { Button } from "@/components/ui/button" import { Button } from "@/components/ui/button"
import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuTrigger } from "@/components/ui/dropdown-menu" import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuTrigger } from "@/components/ui/dropdown-menu"
import { dynamicActivate } from "@/lib/i18n"
import languages from "@/lib/languages" import languages from "@/lib/languages"
import { cn } from "@/lib/utils" import { cn } from "@/lib/utils"
import { useLingui } from "@lingui/react/macro"
import { dynamicActivate } from "@/lib/i18n"
export function LangToggle() { export function LangToggle() {
const { i18n } = useLingui() const { i18n } = useLingui()

View File

@@ -1,19 +1,19 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { Trans } from "@lingui/react/macro" import { Trans } from "@lingui/react/macro"
import { cn } from "@/lib/utils" import { getPagePath } from "@nanostores/router"
import { KeyIcon, LoaderCircle, LockIcon, LogInIcon, MailIcon } from "lucide-react"
import type { AuthMethodsList, AuthProviderInfo, OAuth2AuthConfig } from "pocketbase"
import { useCallback, useEffect, useState } from "react"
import * as v from "valibot"
import { buttonVariants } from "@/components/ui/button" import { buttonVariants } from "@/components/ui/button"
import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger } from "@/components/ui/dialog"
import { Input } from "@/components/ui/input" import { Input } from "@/components/ui/input"
import { Label } from "@/components/ui/label" import { Label } from "@/components/ui/label"
import { KeyIcon, LoaderCircle, LockIcon, LogInIcon, MailIcon } from "lucide-react"
import { $authenticated } from "@/lib/stores"
import * as v from "valibot"
import { toast } from "../ui/use-toast"
import { Dialog, DialogContent, DialogTrigger, DialogHeader, DialogTitle } from "@/components/ui/dialog"
import { useCallback, useEffect, useState } from "react"
import { AuthMethodsList, AuthProviderInfo, OAuth2AuthConfig } from "pocketbase"
import { $router, Link, prependBasePath } from "../router"
import { getPagePath } from "@nanostores/router"
import { pb } from "@/lib/api" import { pb } from "@/lib/api"
import { $authenticated } from "@/lib/stores"
import { cn } from "@/lib/utils"
import { $router, Link, prependBasePath } from "../router"
import { toast } from "../ui/use-toast"
import { OtpInputForm } from "./otp-forms" import { OtpInputForm } from "./otp-forms"
const honeypot = v.literal("") const honeypot = v.literal("")
@@ -83,9 +83,9 @@ export function UserAuthForm({
const result = v.safeParse(Schema, data) const result = v.safeParse(Schema, data)
if (!result.success) { if (!result.success) {
console.log(result) console.log(result)
let errors = {} const errors = {}
for (const issue of result.issues) { for (const issue of result.issues) {
// @ts-ignore // @ts-expect-error
errors[issue.path[0].key] = issue.message errors[issue.path[0].key] = issue.message
} }
setErrors(errors) setErrors(errors)
@@ -96,7 +96,7 @@ export function UserAuthForm({
if (isFirstRun) { if (isFirstRun) {
// check that passwords match // check that passwords match
if (password !== passwordConfirm) { if (password !== passwordConfirm) {
let msg = "Passwords do not match" const msg = "Passwords do not match"
setErrors({ passwordConfirm: msg }) setErrors({ passwordConfirm: msg })
return return
} }

View File

@@ -1,15 +1,14 @@
import { Trans } from "@lingui/react/macro"
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { Trans } from "@lingui/react/macro"
import { LoaderCircle, MailIcon, SendHorizonalIcon } from "lucide-react" import { LoaderCircle, MailIcon, SendHorizonalIcon } from "lucide-react"
import { useCallback, useState } from "react"
import { pb } from "@/lib/api"
import { cn } from "@/lib/utils"
import { buttonVariants } from "../ui/button"
import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger } from "../ui/dialog"
import { Input } from "../ui/input" import { Input } from "../ui/input"
import { Label } from "../ui/label" import { Label } from "../ui/label"
import { useCallback, useState } from "react"
import { toast } from "../ui/use-toast" import { toast } from "../ui/use-toast"
import { buttonVariants } from "../ui/button"
import { cn } from "@/lib/utils"
import { Dialog, DialogHeader } from "../ui/dialog"
import { DialogContent, DialogTrigger, DialogTitle } from "../ui/dialog"
import { pb } from "@/lib/api"
const showLoginFaliedToast = () => { const showLoginFaliedToast = () => {
toast({ toast({

View File

@@ -1,14 +1,14 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { UserAuthForm } from "@/components/login/auth-form"
import { Logo } from "../logo"
import { useEffect, useMemo, useState } from "react"
import { useStore } from "@nanostores/react" import { useStore } from "@nanostores/react"
import ForgotPassword from "./forgot-pass-form" import type { AuthMethodsList } from "pocketbase"
import { $router } from "../router" import { useEffect, useMemo, useState } from "react"
import { AuthMethodsList } from "pocketbase" import { UserAuthForm } from "@/components/login/auth-form"
import { useTheme } from "../theme-provider"
import { pb } from "@/lib/api" import { pb } from "@/lib/api"
import { Logo } from "../logo"
import { ModeToggle } from "../mode-toggle" import { ModeToggle } from "../mode-toggle"
import { $router } from "../router"
import { useTheme } from "../theme-provider"
import ForgotPassword from "./forgot-pass-form"
import { OtpRequestForm } from "./otp-forms" import { OtpRequestForm } from "./otp-forms"
export default function () { export default function () {
@@ -53,7 +53,7 @@ export default function () {
<div className="min-h-svh grid items-center py-12"> <div className="min-h-svh grid items-center py-12">
<div <div
className="grid gap-5 w-full px-4 mx-auto" className="grid gap-5 w-full px-4 mx-auto"
// @ts-ignore // @ts-expect-error
style={{ maxWidth: "21.5em", "--border": theme == "light" ? "hsl(30, 8%, 70%)" : "hsl(220, 3%, 25%)" }} style={{ maxWidth: "21.5em", "--border": theme == "light" ? "hsl(30, 8%, 70%)" : "hsl(220, 3%, 25%)" }}
> >
<div className="absolute top-3 right-3"> <div className="absolute top-3 right-3">

View File

@@ -1,15 +1,15 @@
import { Trans } from "@lingui/react/macro"
import { LoaderCircle, MailIcon, SendHorizonalIcon } from "lucide-react"
import { useCallback, useState } from "react" import { useCallback, useState } from "react"
import { InputOTP, InputOTPGroup, InputOTPSlot } from "@/components/ui/otp"
import { pb } from "@/lib/api" import { pb } from "@/lib/api"
import { $authenticated } from "@/lib/stores" import { $authenticated } from "@/lib/stores"
import { InputOTP, InputOTPGroup, InputOTPSlot } from "@/components/ui/otp"
import { Trans } from "@lingui/react/macro"
import { showLoginFaliedToast } from "./auth-form"
import { cn } from "@/lib/utils" import { cn } from "@/lib/utils"
import { MailIcon, LoaderCircle, SendHorizonalIcon } from "lucide-react" import { $router } from "../router"
import { Label } from "../ui/label"
import { buttonVariants } from "../ui/button" import { buttonVariants } from "../ui/button"
import { Input } from "../ui/input" import { Input } from "../ui/input"
import { $router } from "../router" import { Label } from "../ui/label"
import { showLoginFaliedToast } from "./auth-form"
export function OtpInputForm({ otpId, mfaId }: { otpId: string; mfaId: string }) { export function OtpInputForm({ otpId, mfaId }: { otpId: string; mfaId: string }) {
const [value, setValue] = useState("") const [value, setValue] = useState("")

View File

@@ -1,8 +1,7 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { MoonStarIcon, SunIcon } from "lucide-react" import { MoonStarIcon, SunIcon } from "lucide-react"
import { Button } from "@/components/ui/button"
import { useTheme } from "@/components/theme-provider" import { useTheme } from "@/components/theme-provider"
import { Button } from "@/components/ui/button"
export function ModeToggle() { export function ModeToggle() {
const { theme, setTheme } = useTheme() const { theme, setTheme } = useTheme()

View File

@@ -1,6 +1,5 @@
import { Trans } from "@lingui/react/macro" import { Trans } from "@lingui/react/macro"
import { useState, lazy, Suspense } from "react" import { getPagePath } from "@nanostores/router"
import { Button, buttonVariants } from "@/components/ui/button"
import { import {
DatabaseBackupIcon, DatabaseBackupIcon,
LogOutIcon, LogOutIcon,
@@ -11,23 +10,24 @@ import {
UserIcon, UserIcon,
UsersIcon, UsersIcon,
} from "lucide-react" } from "lucide-react"
import { $router, basePath, Link, prependBasePath } from "./router" import { lazy, Suspense, useState } from "react"
import { LangToggle } from "./lang-toggle" import { Button, buttonVariants } from "@/components/ui/button"
import { ModeToggle } from "./mode-toggle"
import { Logo } from "./logo"
import { cn, runOnce } from "@/lib/utils"
import { isReadOnlyUser, isAdmin, logOut, pb } from "@/lib/api"
import { import {
DropdownMenu, DropdownMenu,
DropdownMenuTrigger,
DropdownMenuContent, DropdownMenuContent,
DropdownMenuLabel,
DropdownMenuSeparator,
DropdownMenuGroup, DropdownMenuGroup,
DropdownMenuItem, DropdownMenuItem,
DropdownMenuLabel,
DropdownMenuSeparator,
DropdownMenuTrigger,
} from "@/components/ui/dropdown-menu" } from "@/components/ui/dropdown-menu"
import { isAdmin, isReadOnlyUser, logOut, pb } from "@/lib/api"
import { cn, runOnce } from "@/lib/utils"
import { AddSystemButton } from "./add-system" import { AddSystemButton } from "./add-system"
import { getPagePath } from "@nanostores/router" import { LangToggle } from "./lang-toggle"
import { Logo } from "./logo"
import { ModeToggle } from "./mode-toggle"
import { $router, basePath, Link, prependBasePath } from "./router"
const CommandPalette = lazy(() => import("./command-palette")) const CommandPalette = lazy(() => import("./command-palette"))

View File

@@ -23,7 +23,7 @@ export const prependBasePath = (path: string) => (basePath + path).replaceAll("/
// prepend base path to routes // prepend base path to routes
for (const route in routes) { for (const route in routes) {
// @ts-ignore need as const above to get nanostores to parse types properly // @ts-expect-error need as const above to get nanostores to parse types properly
routes[route] = prependBasePath(routes[route]) routes[route] = prependBasePath(routes[route])
} }

View File

@@ -3,13 +3,13 @@ import { Trans, useLingui } from "@lingui/react/macro"
import { redirectPage } from "@nanostores/router" import { redirectPage } from "@nanostores/router"
import { import {
CopyIcon, CopyIcon,
ExternalLinkIcon,
FingerprintIcon, FingerprintIcon,
KeyIcon, KeyIcon,
MoreHorizontalIcon, MoreHorizontalIcon,
RotateCwIcon, RotateCwIcon,
ServerIcon, ServerIcon,
Trash2Icon, Trash2Icon,
ExternalLinkIcon,
} from "lucide-react" } from "lucide-react"
import { memo, useEffect, useMemo, useState } from "react" import { memo, useEffect, useMemo, useState } from "react"
import { import {

View File

@@ -52,6 +52,7 @@ import { Input } from "../ui/input"
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "../ui/select" import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "../ui/select"
import { Separator } from "../ui/separator" import { Separator } from "../ui/separator"
import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "../ui/tooltip" import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from "../ui/tooltip"
import NetworkSheet from "./system/network-sheet"
type ChartTimeData = { type ChartTimeData = {
time: number time: number
@@ -564,13 +565,13 @@ export default memo(function SystemDetail({ name }: { name: string }) {
dataPoints={[ dataPoints={[
{ {
label: t({ message: "Write", comment: "Disk write" }), label: t({ message: "Write", comment: "Disk write" }),
dataKey: ({ stats }) => (showMax ? stats?.dwm : stats?.dw), dataKey: ({ stats }: SystemStatsRecord) => (showMax ? stats?.dwm : stats?.dw),
color: 3, color: 3,
opacity: 0.3, opacity: 0.3,
}, },
{ {
label: t({ message: "Read", comment: "Disk read" }), label: t({ message: "Read", comment: "Disk read" }),
dataKey: ({ stats }) => (showMax ? stats?.drm : stats?.dr), dataKey: ({ stats }: SystemStatsRecord) => (showMax ? stats?.drm : stats?.dr),
color: 1, color: 1,
opacity: 0.3, opacity: 0.3,
}, },
@@ -590,7 +591,12 @@ export default memo(function SystemDetail({ name }: { name: string }) {
empty={dataEmpty} empty={dataEmpty}
grid={grid} grid={grid}
title={t`Bandwidth`} title={t`Bandwidth`}
cornerEl={maxValSelect} cornerEl={
<div className="flex gap-2">
{maxValSelect}
<NetworkSheet chartData={chartData} dataEmpty={dataEmpty} grid={grid} maxValues={maxValues} />
</div>
}
description={t`Network traffic of public interfaces`} description={t`Network traffic of public interfaces`}
> >
<AreaChartDefault <AreaChartDefault
@@ -600,7 +606,7 @@ export default memo(function SystemDetail({ name }: { name: string }) {
{ {
label: t`Sent`, label: t`Sent`,
// use bytes if available, otherwise multiply old MB (can remove in future) // use bytes if available, otherwise multiply old MB (can remove in future)
dataKey(data) { dataKey(data: SystemStatsRecord) {
if (showMax) { if (showMax) {
return data?.stats?.bm?.[0] ?? (data?.stats?.nsm ?? 0) * 1024 * 1024 return data?.stats?.bm?.[0] ?? (data?.stats?.nsm ?? 0) * 1024 * 1024
} }
@@ -611,7 +617,7 @@ export default memo(function SystemDetail({ name }: { name: string }) {
}, },
{ {
label: t`Received`, label: t`Received`,
dataKey(data) { dataKey(data: SystemStatsRecord) {
if (showMax) { if (showMax) {
return data?.stats?.bm?.[1] ?? (data?.stats?.nrm ?? 0) * 1024 * 1024 return data?.stats?.bm?.[1] ?? (data?.stats?.nrm ?? 0) * 1024 * 1024
} }
@@ -620,7 +626,9 @@ export default memo(function SystemDetail({ name }: { name: string }) {
color: 2, color: 2,
opacity: 0.2, opacity: 0.2,
}, },
]} ]
// try to place the lesser number in front for better visibility
.sort(() => (systemStats.at(-1)?.stats.b?.[1] ?? 0) - (systemStats.at(-1)?.stats.b?.[0] ?? 0))}
tickFormatter={(val) => { tickFormatter={(val) => {
const { value, unit } = formatBytes(val, true, userSettings.unitNet, false) const { value, unit } = formatBytes(val, true, userSettings.unitNet, false)
return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}` return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}`
@@ -674,6 +682,7 @@ export default memo(function SystemDetail({ name }: { name: string }) {
grid={grid} grid={grid}
title={t`Load Average`} title={t`Load Average`}
description={t`System load averages over time`} description={t`System load averages over time`}
legend={true}
> >
<LoadAverageChart chartData={chartData} /> <LoadAverageChart chartData={chartData} />
</ChartCard> </ChartCard>
@@ -687,6 +696,7 @@ export default memo(function SystemDetail({ name }: { name: string }) {
title={t`Temperature`} title={t`Temperature`}
description={t`Temperatures of system sensors`} description={t`Temperatures of system sensors`}
cornerEl={<FilterBar store={$temperatureFilter} />} cornerEl={<FilterBar store={$temperatureFilter} />}
legend={Object.keys(systemStats.at(-1)?.stats.t ?? {}).length < 12}
> >
<TemperatureChart chartData={chartData} /> <TemperatureChart chartData={chartData} />
</ChartCard> </ChartCard>
@@ -879,7 +889,7 @@ function FilterBar({ store = $containerFilter }: { store?: typeof $containerFilt
return ( return (
<> <>
<Input placeholder={t`Filter...`} className="ps-4 pe-8" onChange={handleChange} ref={inputRef} /> <Input placeholder={t`Filter...`} className="ps-4 pe-8 w-full sm:w-44" onChange={handleChange} ref={inputRef} />
{containerFilter && ( {containerFilter && (
<Button <Button
type="button" type="button"
@@ -905,7 +915,7 @@ const SelectAvgMax = memo(({ max }: { max: boolean }) => {
const Icon = max ? ChartMax : ChartAverage const Icon = max ? ChartMax : ChartAverage
return ( return (
<Select value={max ? "max" : "avg"} onValueChange={(e) => $maxValues.set(e === "max")}> <Select value={max ? "max" : "avg"} onValueChange={(e) => $maxValues.set(e === "max")}>
<SelectTrigger className="relative ps-10 pe-5"> <SelectTrigger className="relative ps-10 pe-5 w-full sm:w-44">
<Icon className="h-4 w-4 absolute start-4 top-1/2 -translate-y-1/2 opacity-85" /> <Icon className="h-4 w-4 absolute start-4 top-1/2 -translate-y-1/2 opacity-85" />
<SelectValue /> <SelectValue />
</SelectTrigger> </SelectTrigger>
@@ -921,13 +931,15 @@ const SelectAvgMax = memo(({ max }: { max: boolean }) => {
) )
}) })
function ChartCard({ export function ChartCard({
title, title,
description, description,
children, children,
grid, grid,
empty, empty,
cornerEl, cornerEl,
legend,
className,
}: { }: {
title: string title: string
description: string description: string
@@ -935,17 +947,22 @@ function ChartCard({
grid?: boolean grid?: boolean
empty?: boolean empty?: boolean
cornerEl?: JSX.Element | null cornerEl?: JSX.Element | null
legend?: boolean
className?: string
}) { }) {
const { isIntersecting, ref } = useIntersectionObserver() const { isIntersecting, ref } = useIntersectionObserver()
return ( return (
<Card className={cn("pb-2 sm:pb-4 odd:last-of-type:col-span-full", { "col-span-full": !grid })} ref={ref}> <Card
className={cn("pb-2 sm:pb-4 odd:last-of-type:col-span-full min-h-full", { "col-span-full": !grid }, className)}
ref={ref}
>
<CardHeader className="pb-5 pt-4 gap-1 relative max-sm:py-3 max-sm:px-4"> <CardHeader className="pb-5 pt-4 gap-1 relative max-sm:py-3 max-sm:px-4">
<CardTitle className="text-xl sm:text-2xl">{title}</CardTitle> <CardTitle className="text-xl sm:text-2xl">{title}</CardTitle>
<CardDescription>{description}</CardDescription> <CardDescription>{description}</CardDescription>
{cornerEl && <div className="relative py-1 block sm:w-44 sm:absolute sm:top-3.5 sm:end-3.5">{cornerEl}</div>} {cornerEl && <div className="py-1 grid sm:justify-end sm:absolute sm:top-3.5 sm:end-3.5">{cornerEl}</div>}
</CardHeader> </CardHeader>
<div className="ps-0 w-[calc(100%-1.5em)] h-48 md:h-52 relative group"> <div className={cn("ps-0 w-[calc(100%-1.5em)] relative group", legend ? "h-54 md:h-56" : "h-48 md:h-52")}>
{ {
<Spinner <Spinner
msg={empty ? t`Waiting for enough records to display` : undefined} msg={empty ? t`Waiting for enough records to display` : undefined}

View File

@@ -0,0 +1,153 @@
import { t } from "@lingui/core/macro"
import { useStore } from "@nanostores/react"
import { MoreHorizontalIcon } from "lucide-react"
import { memo, useRef, useState } from "react"
import AreaChartDefault from "@/components/charts/area-chart"
import ChartTimeSelect from "@/components/charts/chart-time-select"
import { useNetworkInterfaces } from "@/components/charts/hooks"
import { Button } from "@/components/ui/button"
import { Sheet, SheetContent, SheetTrigger } from "@/components/ui/sheet"
import { $userSettings } from "@/lib/stores"
import { decimalString, formatBytes, toFixedFloat } from "@/lib/utils"
import type { ChartData } from "@/types"
import { ChartCard } from "../system"
export default memo(function NetworkSheet({
chartData,
dataEmpty,
grid,
maxValues,
}: {
chartData: ChartData
dataEmpty: boolean
grid: boolean
maxValues: boolean
}) {
const [netInterfacesOpen, setNetInterfacesOpen] = useState(false)
const userSettings = useStore($userSettings)
const netInterfaces = useNetworkInterfaces(chartData.systemStats.at(-1)?.stats?.ni ?? {})
const showNetLegend = netInterfaces.length > 0
const hasOpened = useRef(false)
if (netInterfacesOpen && !hasOpened.current) {
hasOpened.current = true
}
if (!netInterfaces.length) {
return null
}
return (
<Sheet open={netInterfacesOpen} onOpenChange={setNetInterfacesOpen}>
<SheetTrigger asChild>
<Button
variant="outline"
size="icon"
className="shrink-0 absolute top-3 end-3 sm:inline-flex sm:top-0 sm:end-0"
>
<MoreHorizontalIcon />
</Button>
</SheetTrigger>
{hasOpened.current && (
<SheetContent className="overflow-auto w-200 !max-w-full p-4 sm:p-6">
<ChartTimeSelect className="w-[calc(100%-2em)]" />
<ChartCard
empty={dataEmpty}
grid={grid}
title={t`Download`}
description={t`Network traffic of public interfaces`}
legend={showNetLegend}
className="min-h-auto"
>
<AreaChartDefault
chartData={chartData}
maxToggled={maxValues}
itemSorter={(a, b) => b.value - a.value}
dataPoints={netInterfaces.data(1)}
legend={showNetLegend}
tickFormatter={(val) => {
const { value, unit } = formatBytes(val, true, userSettings.unitNet, false)
return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}`
}}
contentFormatter={({ value }) => {
const { value: convertedValue, unit } = formatBytes(value, true, userSettings.unitNet, false)
return `${decimalString(convertedValue, convertedValue >= 100 ? 1 : 2)} ${unit}`
}}
/>
</ChartCard>
<ChartCard
empty={dataEmpty}
grid={grid}
title={t`Upload`}
description={t`Network traffic of public interfaces`}
legend={showNetLegend}
className="min-h-auto"
>
<AreaChartDefault
chartData={chartData}
maxToggled={maxValues}
itemSorter={(a, b) => b.value - a.value}
legend={showNetLegend}
dataPoints={netInterfaces.data(0)}
tickFormatter={(val) => {
const { value, unit } = formatBytes(val, true, userSettings.unitNet, false)
return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}`
}}
contentFormatter={({ value }) => {
const { value: convertedValue, unit } = formatBytes(value, true, userSettings.unitNet, false)
return `${decimalString(convertedValue, convertedValue >= 100 ? 1 : 2)} ${unit}`
}}
/>
</ChartCard>
<ChartCard
empty={dataEmpty}
grid={grid}
title={t`Cumulative Download`}
description={t`Total data received for each interface`}
legend={showNetLegend}
className="min-h-auto"
>
<AreaChartDefault
chartData={chartData}
legend={showNetLegend}
dataPoints={netInterfaces.data(3)}
tickFormatter={(val) => {
const { value, unit } = formatBytes(val, false, userSettings.unitNet, false)
return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}`
}}
contentFormatter={({ value }) => {
const { value: convertedValue, unit } = formatBytes(value, false, userSettings.unitNet, false)
return `${decimalString(convertedValue, convertedValue >= 100 ? 1 : 2)} ${unit}`
}}
/>
</ChartCard>
<ChartCard
empty={dataEmpty}
grid={grid}
title={t`Cumulative Upload`}
description={t`Total data sent for each interface`}
legend={showNetLegend}
className="min-h-auto"
>
<AreaChartDefault
chartData={chartData}
legend={showNetLegend}
dataPoints={netInterfaces.data(2)}
tickFormatter={(val) => {
const { value, unit } = formatBytes(val, false, userSettings.unitNet, false)
return `${toFixedFloat(value, value >= 10 ? 0 : 1)} ${unit}`
}}
contentFormatter={({ value }) => {
const { value: convertedValue, unit } = formatBytes(value, false, userSettings.unitNet, false)
return `${decimalString(convertedValue, convertedValue >= 100 ? 1 : 2)} ${unit}`
}}
/>
</ChartCard>
</SheetContent>
)}
</Sheet>
)
})

View File

@@ -1,5 +1,5 @@
import { cn } from "@/lib/utils"
import { LoaderCircleIcon } from "lucide-react" import { LoaderCircleIcon } from "lucide-react"
import { cn } from "@/lib/utils"
export default function ({ msg, className }: { msg?: string; className?: string }) { export default function ({ msg, className }: { msg?: string; className?: string }) {
return ( return (

View File

@@ -1,6 +1,9 @@
import { SystemRecord } from "@/types" import { t } from "@lingui/core/macro"
import { CellContext, ColumnDef, HeaderContext } from "@tanstack/react-table" import { Trans, useLingui } from "@lingui/react/macro"
import { ClassValue } from "clsx" import { useStore } from "@nanostores/react"
import { getPagePath } from "@nanostores/router"
import type { CellContext, ColumnDef, HeaderContext } from "@tanstack/react-table"
import type { ClassValue } from "clsx"
import { import {
ArrowUpDownIcon, ArrowUpDownIcon,
CopyIcon, CopyIcon,
@@ -15,7 +18,10 @@ import {
Trash2Icon, Trash2Icon,
WifiIcon, WifiIcon,
} from "lucide-react" } from "lucide-react"
import { Button } from "../ui/button" import { memo, useMemo, useRef, useState } from "react"
import { isReadOnlyUser, pb } from "@/lib/api"
import { MeterState, SystemStatus } from "@/lib/enums"
import { $longestSystemNameLen, $userSettings } from "@/lib/stores"
import { import {
cn, cn,
copyToClipboard, copyToClipboard,
@@ -25,24 +31,12 @@ import {
getMeterState, getMeterState,
parseSemVer, parseSemVer,
} from "@/lib/utils" } from "@/lib/utils"
import { EthernetIcon, GpuIcon, HourglassIcon, ThermometerIcon } from "../ui/icons" import type { SystemRecord } from "@/types"
import { useStore } from "@nanostores/react"
import { $longestSystemNameLen, $userSettings } from "@/lib/stores"
import { Trans, useLingui } from "@lingui/react/macro"
import { useMemo, useRef, useState } from "react"
import { memo } from "react"
import {
DropdownMenu,
DropdownMenuContent,
DropdownMenuItem,
DropdownMenuSeparator,
DropdownMenuTrigger,
} from "../ui/dropdown-menu"
import AlertButton from "../alerts/alert-button"
import { Dialog } from "../ui/dialog"
import { SystemDialog } from "../add-system" import { SystemDialog } from "../add-system"
import { AlertDialog } from "../ui/alert-dialog" import AlertButton from "../alerts/alert-button"
import { $router, Link } from "../router"
import { import {
AlertDialog,
AlertDialogAction, AlertDialogAction,
AlertDialogCancel, AlertDialogCancel,
AlertDialogContent, AlertDialogContent,
@@ -51,12 +45,16 @@ import {
AlertDialogHeader, AlertDialogHeader,
AlertDialogTitle, AlertDialogTitle,
} from "../ui/alert-dialog" } from "../ui/alert-dialog"
import { buttonVariants } from "../ui/button" import { Button, buttonVariants } from "../ui/button"
import { t } from "@lingui/core/macro" import { Dialog } from "../ui/dialog"
import { MeterState, SystemStatus } from "@/lib/enums" import {
import { $router, Link } from "../router" DropdownMenu,
import { getPagePath } from "@nanostores/router" DropdownMenuContent,
import { isReadOnlyUser, pb } from "@/lib/api" DropdownMenuItem,
DropdownMenuSeparator,
DropdownMenuTrigger,
} from "../ui/dropdown-menu"
import { EthernetIcon, GpuIcon, HourglassIcon, ThermometerIcon } from "../ui/icons"
const STATUS_COLORS = { const STATUS_COLORS = {
[SystemStatus.Up]: "bg-green-500", [SystemStatus.Up]: "bg-green-500",
@@ -290,7 +288,7 @@ export default function SystemsTableColumns(viewMode: "table" | "grid"): ColumnD
}, },
{ {
id: "actions", id: "actions",
// @ts-ignore // @ts-expect-error
name: () => t({ message: "Actions", comment: "Table column" }), name: () => t({ message: "Actions", comment: "Table column" }),
size: 50, size: 50,
cell: ({ row }) => ( cell: ({ row }) => (
@@ -305,7 +303,7 @@ export default function SystemsTableColumns(viewMode: "table" | "grid"): ColumnD
function sortableHeader(context: HeaderContext<SystemRecord, unknown>) { function sortableHeader(context: HeaderContext<SystemRecord, unknown>) {
const { column } = context const { column } = context
// @ts-ignore // @ts-expect-error
const { Icon, hideSort, name }: { Icon: React.ElementType; name: () => string; hideSort: boolean } = column.columnDef const { Icon, hideSort, name }: { Icon: React.ElementType; name: () => string; hideSort: boolean } = column.columnDef
return ( return (
<Button <Button
@@ -353,7 +351,7 @@ export function IndicatorDot({ system, className }: { system: SystemRecord; clas
export const ActionsButton = memo(({ system }: { system: SystemRecord }) => { export const ActionsButton = memo(({ system }: { system: SystemRecord }) => {
const [deleteOpen, setDeleteOpen] = useState(false) const [deleteOpen, setDeleteOpen] = useState(false)
const [editOpen, setEditOpen] = useState(false) const [editOpen, setEditOpen] = useState(false)
let editOpened = useRef(false) const editOpened = useRef(false)
const { t } = useLingui() const { t } = useLingui()
const { id, status, host, name } = system const { id, status, host, name } = system

View File

@@ -1,17 +1,31 @@
import { Trans, useLingui } from "@lingui/react/macro"
import { useStore } from "@nanostores/react"
import { getPagePath } from "@nanostores/router"
import { import {
ColumnDef, type ColumnDef,
ColumnFiltersState, type ColumnFiltersState,
getFilteredRowModel,
SortingState,
getSortedRowModel,
flexRender, flexRender,
VisibilityState,
getCoreRowModel, getCoreRowModel,
getFilteredRowModel,
getSortedRowModel,
type Row,
type SortingState,
type Table as TableType,
useReactTable, useReactTable,
Row, type VisibilityState,
Table as TableType,
} from "@tanstack/react-table" } from "@tanstack/react-table"
import { TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table" import { useVirtualizer, type VirtualItem } from "@tanstack/react-virtual"
import {
ArrowDownIcon,
ArrowUpDownIcon,
ArrowUpIcon,
EyeIcon,
FilterIcon,
LayoutGridIcon,
LayoutListIcon,
Settings2Icon,
} from "lucide-react"
import { memo, useEffect, useMemo, useRef, useState } from "react"
import { Button } from "@/components/ui/button" import { Button } from "@/components/ui/button"
import { import {
DropdownMenu, DropdownMenu,
@@ -24,30 +38,16 @@ import {
DropdownMenuSeparator, DropdownMenuSeparator,
DropdownMenuTrigger, DropdownMenuTrigger,
} from "@/components/ui/dropdown-menu" } from "@/components/ui/dropdown-menu"
import { SystemRecord } from "@/types"
import {
ArrowUpDownIcon,
LayoutGridIcon,
LayoutListIcon,
ArrowDownIcon,
ArrowUpIcon,
Settings2Icon,
EyeIcon,
FilterIcon,
} from "lucide-react"
import { memo, useEffect, useMemo, useRef, useState } from "react"
import { $pausedSystems, $downSystems, $upSystems, $systems } from "@/lib/stores"
import { useStore } from "@nanostores/react"
import { cn, runOnce, useBrowserStorage } from "@/lib/utils"
import { $router, Link } from "../router"
import { useLingui, Trans } from "@lingui/react/macro"
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "../ui/card"
import { Input } from "@/components/ui/input" import { Input } from "@/components/ui/input"
import { getPagePath } from "@nanostores/router" import { TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table"
import SystemsTableColumns, { ActionsButton, IndicatorDot } from "./systems-table-columns"
import AlertButton from "../alerts/alert-button"
import { SystemStatus } from "@/lib/enums" import { SystemStatus } from "@/lib/enums"
import { useVirtualizer, VirtualItem } from "@tanstack/react-virtual" import { $downSystems, $pausedSystems, $systems, $upSystems } from "@/lib/stores"
import { cn, runOnce, useBrowserStorage } from "@/lib/utils"
import type { SystemRecord } from "@/types"
import AlertButton from "../alerts/alert-button"
import { $router, Link } from "../router"
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "../ui/card"
import SystemsTableColumns, { ActionsButton, IndicatorDot } from "./systems-table-columns"
type ViewMode = "table" | "grid" type ViewMode = "table" | "grid"
type StatusFilter = "all" | SystemRecord["status"] type StatusFilter = "all" | SystemRecord["status"]
@@ -309,69 +309,63 @@ export default function SystemsTable() {
) )
} }
const AllSystemsTable = memo(function ({ const AllSystemsTable = memo(
table, ({ table, rows, colLength }: { table: TableType<SystemRecord>; rows: Row<SystemRecord>[]; colLength: number }) => {
rows, // The virtualizer will need a reference to the scrollable container element
colLength, const scrollRef = useRef<HTMLDivElement>(null)
}: {
table: TableType<SystemRecord>
rows: Row<SystemRecord>[]
colLength: number
}) {
// The virtualizer will need a reference to the scrollable container element
const scrollRef = useRef<HTMLDivElement>(null)
const virtualizer = useVirtualizer<HTMLDivElement, HTMLTableRowElement>({ const virtualizer = useVirtualizer<HTMLDivElement, HTMLTableRowElement>({
count: rows.length, count: rows.length,
estimateSize: () => (rows.length > 10 ? 56 : 60), estimateSize: () => (rows.length > 10 ? 56 : 60),
getScrollElement: () => scrollRef.current, getScrollElement: () => scrollRef.current,
overscan: 5, overscan: 5,
}) })
const virtualRows = virtualizer.getVirtualItems() const virtualRows = virtualizer.getVirtualItems()
const paddingTop = Math.max(0, virtualRows[0]?.start ?? 0 - virtualizer.options.scrollMargin) const paddingTop = Math.max(0, virtualRows[0]?.start ?? 0 - virtualizer.options.scrollMargin)
const paddingBottom = Math.max(0, virtualizer.getTotalSize() - (virtualRows[virtualRows.length - 1]?.end ?? 0)) const paddingBottom = Math.max(0, virtualizer.getTotalSize() - (virtualRows[virtualRows.length - 1]?.end ?? 0))
return ( return (
<div <div
className={cn( className={cn(
"h-min max-h-[calc(100dvh-17rem)] max-w-full relative overflow-auto border rounded-md", "h-min max-h-[calc(100dvh-17rem)] max-w-full relative overflow-auto border rounded-md",
// don't set min height if there are less than 2 rows, do set if we need to display the empty state // don't set min height if there are less than 2 rows, do set if we need to display the empty state
(!rows.length || rows.length > 2) && "min-h-50" (!rows.length || rows.length > 2) && "min-h-50"
)} )}
ref={scrollRef} ref={scrollRef}
> >
{/* add header height to table size */} {/* add header height to table size */}
<div style={{ height: `${virtualizer.getTotalSize() + 50}px`, paddingTop, paddingBottom }}> <div style={{ height: `${virtualizer.getTotalSize() + 50}px`, paddingTop, paddingBottom }}>
<table className="text-sm w-full h-full"> <table className="text-sm w-full h-full">
<SystemsTableHead table={table} colLength={colLength} /> <SystemsTableHead table={table} colLength={colLength} />
<TableBody onMouseEnter={preloadSystemDetail}> <TableBody onMouseEnter={preloadSystemDetail}>
{rows.length ? ( {rows.length ? (
virtualRows.map((virtualRow) => { virtualRows.map((virtualRow) => {
const row = rows[virtualRow.index] as Row<SystemRecord> const row = rows[virtualRow.index] as Row<SystemRecord>
return ( return (
<SystemTableRow <SystemTableRow
key={row.id} key={row.id}
row={row} row={row}
virtualRow={virtualRow} virtualRow={virtualRow}
length={rows.length} length={rows.length}
colLength={colLength} colLength={colLength}
/> />
) )
}) })
) : ( ) : (
<TableRow> <TableRow>
<TableCell colSpan={colLength} className="h-37 text-center pointer-events-none"> <TableCell colSpan={colLength} className="h-37 text-center pointer-events-none">
<Trans>No systems found.</Trans> <Trans>No systems found.</Trans>
</TableCell> </TableCell>
</TableRow> </TableRow>
)} )}
</TableBody> </TableBody>
</table> </table>
</div>
</div> </div>
</div> )
) }
}) )
function SystemsTableHead({ table, colLength }: { table: TableType<SystemRecord>; colLength: number }) { function SystemsTableHead({ table, colLength }: { table: TableType<SystemRecord>; colLength: number }) {
const { i18n } = useLingui() const { i18n } = useLingui()
@@ -395,42 +389,44 @@ function SystemsTableHead({ table, colLength }: { table: TableType<SystemRecord>
}, [i18n.locale, colLength]) }, [i18n.locale, colLength])
} }
const SystemTableRow = memo(function ({ const SystemTableRow = memo(
row, ({
virtualRow, row,
colLength, virtualRow,
}: { colLength,
row: Row<SystemRecord> }: {
virtualRow: VirtualItem row: Row<SystemRecord>
length: number virtualRow: VirtualItem
colLength: number length: number
}) { colLength: number
const system = row.original }) => {
const { t } = useLingui() const system = row.original
return useMemo(() => { const { t } = useLingui()
return ( return useMemo(() => {
<TableRow return (
// data-state={row.getIsSelected() && "selected"} <TableRow
className={cn("cursor-pointer transition-opacity relative safari:transform-3d", { // data-state={row.getIsSelected() && "selected"}
"opacity-50": system.status === SystemStatus.Paused, className={cn("cursor-pointer transition-opacity relative safari:transform-3d", {
})} "opacity-50": system.status === SystemStatus.Paused,
> })}
{row.getVisibleCells().map((cell) => ( >
<TableCell {row.getVisibleCells().map((cell) => (
key={cell.id} <TableCell
style={{ key={cell.id}
width: cell.column.getSize(), style={{
height: virtualRow.size, width: cell.column.getSize(),
}} height: virtualRow.size,
className="py-0" }}
> className="py-0"
{flexRender(cell.column.columnDef.cell, cell.getContext())} >
</TableCell> {flexRender(cell.column.columnDef.cell, cell.getContext())}
))} </TableCell>
</TableRow> ))}
) </TableRow>
}, [system, system.status, colLength, t]) )
}) }, [system, system.status, colLength, t])
}
)
const SystemCard = memo( const SystemCard = memo(
({ row, table, colLength }: { row: Row<SystemRecord>; table: TableType<SystemRecord>; colLength: number }) => { ({ row, table, colLength }: { row: Row<SystemRecord>; table: TableType<SystemRecord>; colLength: number }) => {
@@ -471,7 +467,7 @@ const SystemCard = memo(
if (!column.getIsVisible() || column.id === "system" || column.id === "actions") return null if (!column.getIsVisible() || column.id === "system" || column.id === "actions") return null
const cell = row.getAllCells().find((cell) => cell.column.id === column.id) const cell = row.getAllCells().find((cell) => cell.column.id === column.id)
if (!cell) return null if (!cell) return null
// @ts-ignore // @ts-expect-error
const { Icon, name } = column.columnDef as ColumnDef<SystemRecord, unknown> const { Icon, name } = column.columnDef as ColumnDef<SystemRecord, unknown>
return ( return (
<> <>

View File

@@ -1,6 +1,7 @@
import { t } from "@lingui/core/macro" import { t } from "@lingui/core/macro"
import { type ClassValue, clsx } from "clsx" import { type ClassValue, clsx } from "clsx"
import { timeDay, timeHour } from "d3-time" import { timeDay, timeHour } from "d3-time"
import { listenKeys } from "nanostores"
import { useEffect, useState } from "react" import { useEffect, useState } from "react"
import { twMerge } from "tailwind-merge" import { twMerge } from "tailwind-merge"
import { prependBasePath } from "@/components/router" import { prependBasePath } from "@/components/router"
@@ -8,7 +9,6 @@ import { toast } from "@/components/ui/use-toast"
import type { ChartTimeData, FingerprintRecord, SemVer, SystemRecord } from "@/types" import type { ChartTimeData, FingerprintRecord, SemVer, SystemRecord } from "@/types"
import { HourFormat, MeterState, Unit } from "./enums" import { HourFormat, MeterState, Unit } from "./enums"
import { $copyContent, $userSettings } from "./stores" import { $copyContent, $userSettings } from "./stores"
import { listenKeys } from "nanostores"
export const FAVICON_DEFAULT = "favicon.svg" export const FAVICON_DEFAULT = "favicon.svg"
export const FAVICON_GREEN = "favicon-green.svg" export const FAVICON_GREEN = "favicon-green.svg"

View File

@@ -363,6 +363,14 @@ msgstr "أنشئت"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "حرج (%)" msgstr "حرج (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "التنزيل التراكمي"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "الرفع التراكمي"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "معطل"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "معطل ({downSystemsLength})" msgstr "معطل ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "تنزيل"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "المدة" msgstr "المدة"
@@ -452,6 +464,7 @@ msgstr "تعديل"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "البريد الإشباكي" msgstr "البريد الإشباكي"
@@ -472,6 +485,10 @@ msgstr "أدخل عنوان البريد الإشباكي لإعادة تعيي
msgid "Enter email address..." msgid "Enter email address..."
msgstr "أدخل عنوان البريد الإشباكي..." msgstr "أدخل عنوان البريد الإشباكي..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "أدخل كلمة المرور لمرة واحدة الخاصة بك."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "لمدة <0>{min}</0> {min, plural, one {دقيقة} other {دقائق}}
msgid "Forgot password?" msgid "Forgot password?"
msgstr "هل نسيت كلمة المرور؟" msgstr "هل نسيت كلمة المرور؟"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "أمر FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "إدارة تفضيلات العرض والإشعارات." msgstr "إدارة تفضيلات العرض والإشعارات."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "تعليمات الإعداد اليدوي" msgstr "تعليمات الإعداد اليدوي"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "حركة مرور الشبكة لحاويات الدوكر" msgstr "حركة مرور الشبكة لحاويات الدوكر"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "حركة مرور الشبكة للواجهات العامة" msgstr "حركة مرور الشبكة للواجهات العامة"
@@ -715,6 +741,10 @@ msgstr "دعم OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "في كل إعادة تشغيل، سيتم تحديث الأنظمة في قاعدة البيانات لتتطابق مع الأنظمة المعرفة في الملف." msgstr "في كل إعادة تشغيل، سيتم تحديث الأنظمة في قاعدة البيانات لتتطابق مع الأنظمة المعرفة في الملف."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "كلمة مرور لمرة واحدة"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "قراءة"
msgid "Received" msgid "Received"
msgstr "تم الاستلام" msgstr "تم الاستلام"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "طلب كلمة مرور لمرة واحدة"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "طلب OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "إعادة تعيين كلمة المرور" msgstr "إعادة تعيين كلمة المرور"
@@ -888,10 +926,6 @@ msgstr "تم الإرسال"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "تعيين عتبات النسبة المئوية لألوان العداد." msgstr "تعيين عتبات النسبة المئوية لألوان العداد."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "يحدد النطاق الزمني الافتراضي للرسوم البيانية عند عرض النظام."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "معدل نقل {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "معدل نقل نظام الملفات الجذر" msgstr "معدل نقل نظام الملفات الجذر"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "تنسيق الوقت"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "إلى البريد الإشباكي" msgstr "إلى البريد الإشباكي"
@@ -1034,6 +1072,14 @@ msgstr "تسمح الرموز المميزة للوكلاء بالاتصال و
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "تُستخدم الرموز المميزة والبصمات للمصادقة على اتصالات WebSocket إلى المحور." msgstr "تُستخدم الرموز المميزة والبصمات للمصادقة على اتصالات WebSocket إلى المحور."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "إجمالي البيانات المستلمة لكل واجهة"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "إجمالي البيانات المرسلة لكل واجهة"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "يتم التفعيل عندما يتجاوز متوسط التحميل لمدة دقيقة واحدة عتبة معينة" msgstr "يتم التفعيل عندما يتجاوز متوسط التحميل لمدة دقيقة واحدة عتبة معينة"
@@ -1048,7 +1094,7 @@ msgstr "يتم التفعيل عندما يتجاوز متوسط التحميل
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when any sensor exceeds a threshold" msgid "Triggers when any sensor exceeds a threshold"
msgstr "يتم التفعيل عندما <EFBFBD><EFBFBD>تجاوز أي مستشعر عتبة معينة" msgstr "يتم التفعيل عندما يتجاوز أي مستشعر عتبة معينة"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when combined up/down exceeds a threshold" msgid "Triggers when combined up/down exceeds a threshold"
@@ -1095,6 +1141,10 @@ msgstr "قيد التشغيل"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "قيد التشغيل ({upSystemsLength})" msgstr "قيد التشغيل ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "رفع"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "مدة التشغيل" msgstr "مدة التشغيل"

View File

@@ -363,6 +363,14 @@ msgstr "Създаден"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Критично (%)" msgstr "Критично (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Кумулативно изтегляне"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Кумулативно качване"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Офлайн"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Офлайн ({downSystemsLength})" msgstr "Офлайн ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Изтегляне"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Продължителност" msgstr "Продължителност"
@@ -452,6 +464,7 @@ msgstr "Редактирай"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Имейл" msgstr "Имейл"
@@ -472,6 +485,10 @@ msgstr "Въведи имейл адрес за да нулираш парола
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Въведи имейл адрес..." msgstr "Въведи имейл адрес..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Въведете Вашата еднократна парола."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "За <0>{min}</0> {min, plural, one {минута} other {минути}}
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Забравена парола?" msgstr "Забравена парола?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD команда"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Управление на предпочитанията за показване и уведомяване." msgstr "Управление на предпочитанията за показване и уведомяване."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Инструкции за ръчна настройка" msgstr "Инструкции за ръчна настройка"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Мрежов трафик на docker контейнери" msgstr "Мрежов трафик на docker контейнери"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Мрежов трафик на публични интерфейси" msgstr "Мрежов трафик на публични интерфейси"
@@ -715,6 +741,10 @@ msgstr "Поддръжка на OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "На всеки рестарт, системите в датабазата ще бъдат обновени да съвпадат със системите зададени във файла." msgstr "На всеки рестарт, системите в датабазата ще бъдат обновени да съвпадат със системите зададени във файла."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Еднократна парола"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Прочети"
msgid "Received" msgid "Received"
msgstr "Получени" msgstr "Получени"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Заявка за еднократна парола"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Заявка OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Нулиране на парола" msgstr "Нулиране на парола"
@@ -888,10 +926,6 @@ msgstr "Изпратени"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Задайте процентни прагове за цветовете на измервателните уреди." msgstr "Задайте процентни прагове за цветовете на измервателните уреди."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Задава диапазона за време за диаграмите, когато се разглежда система."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Пропускателна способност на {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Пропускателна способност на root файловата система" msgstr "Пропускателна способност на root файловата система"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Формат на времето"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "До имейл(ите)" msgstr "До имейл(ите)"
@@ -1034,6 +1072,14 @@ msgstr "Токените позволяват на агентите да се с
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Токените и пръстовите отпечатъци се използват за удостоверяване на WebSocket връзките към концентратора." msgstr "Токените и пръстовите отпечатъци се използват за удостоверяване на WebSocket връзките към концентратора."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Общо получени данни за всеки интерфейс"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Общо изпратени данни за всеки интерфейс"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Задейства се, когато употребата на паметта за 1 минута надвиши зададен праг" msgstr "Задейства се, когато употребата на паметта за 1 минута надвиши зададен праг"
@@ -1095,6 +1141,10 @@ msgstr "Нагоре"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Нагоре ({upSystemsLength})" msgstr "Нагоре ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Качване"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Време на работа" msgstr "Време на работа"

View File

@@ -363,6 +363,14 @@ msgstr "Vytvořeno"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritické (%)" msgstr "Kritické (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativní stažení"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativní odeslání"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Nefunkční"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Nefunkční ({downSystemsLength})" msgstr "Nefunkční ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Stažení"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Doba trvání" msgstr "Doba trvání"
@@ -452,6 +464,7 @@ msgstr "Upravit"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Zadejte e-mailovou adresu pro obnovu hesla"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Zadejte e-mailovou adresu..." msgstr "Zadejte e-mailovou adresu..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Zadejte Vaše jednorázové heslo."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Za <0>{min}</0> {min, plural, one {minutu} few {minuty} other {minut}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Zapomněli jste heslo?" msgstr "Zapomněli jste heslo?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD příkaz"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Správa nastavení zobrazení a oznámení." msgstr "Správa nastavení zobrazení a oznámení."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Pokyny k manuálnímu nastavení" msgstr "Pokyny k manuálnímu nastavení"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Síťový provoz kontejnerů docker" msgstr "Síťový provoz kontejnerů docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Síťový provoz veřejných rozhraní" msgstr "Síťový provoz veřejných rozhraní"
@@ -715,6 +741,10 @@ msgstr "Podpora OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Při každém restartu budou systémy v databázi aktualizovány tak, aby odpovídaly systémům definovaným v souboru." msgstr "Při každém restartu budou systémy v databázi aktualizovány tak, aby odpovídaly systémům definovaným v souboru."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Jednorázové heslo"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Číst"
msgid "Received" msgid "Received"
msgstr "Přijato" msgstr "Přijato"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Požádat o jednorázové heslo"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Požádat OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Obnovit heslo" msgstr "Obnovit heslo"
@@ -888,10 +926,6 @@ msgstr "Odeslat"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Nastavte procentuální prahové hodnoty pro barvy měřičů." msgstr "Nastavte procentuální prahové hodnoty pro barvy měřičů."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Nastaví výchozí časový rozsah grafů, když je systém zobrazen."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Propustnost {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Propustnost kořenového souborového systému" msgstr "Propustnost kořenového souborového systému"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Formát času"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Na email(y)" msgstr "Na email(y)"
@@ -1034,6 +1072,14 @@ msgstr "Tokeny umožňují agentům připojení a registraci. Otisky jsou stabil
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokeny a otisky slouží k ověření připojení WebSocket k uzlu." msgstr "Tokeny a otisky slouží k ověření připojení WebSocket k uzlu."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Celkový přijatý objem dat pro každé rozhraní"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Celkový odeslaný objem dat pro každé rozhraní"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Spustí se, když využití paměti během 1 minuty překročí prahovou hodnotu" msgstr "Spustí se, když využití paměti během 1 minuty překročí prahovou hodnotu"
@@ -1095,6 +1141,10 @@ msgstr "Funkční"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Funkční ({upSystemsLength})" msgstr "Funkční ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Odeslání"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Doba provozu" msgstr "Doba provozu"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritisk (%)" msgstr "Kritisk (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativ download"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativ upload"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Nede"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Download"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr "Rediger"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-mail" msgstr "E-mail"
@@ -472,6 +485,10 @@ msgstr "Indtast e-mailadresse for at nulstille adgangskoden"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Indtast e-mailadresse..." msgstr "Indtast e-mailadresse..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Indtast din engangsadgangskode."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "For <0>{min}</0> {min, plural, one {minut} other {minutter}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Glemt adgangskode?" msgstr "Glemt adgangskode?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD kommando"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Administrer display og notifikationsindstillinger." msgstr "Administrer display og notifikationsindstillinger."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Manuel opsætningsvejledning" msgstr "Manuel opsætningsvejledning"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Netværkstrafik af dockercontainere" msgstr "Netværkstrafik af dockercontainere"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Netværkstrafik af offentlige grænseflader" msgstr "Netværkstrafik af offentlige grænseflader"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC understøttelse"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Ved hver genstart vil systemer i databasen blive opdateret til at matche de systemer, der er defineret i filen." msgstr "Ved hver genstart vil systemer i databasen blive opdateret til at matche de systemer, der er defineret i filen."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Engangsadgangskode"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Læs"
msgid "Received" msgid "Received"
msgstr "Modtaget" msgstr "Modtaget"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Anmod om engangsadgangskode"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Anmod OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Nulstil adgangskode" msgstr "Nulstil adgangskode"
@@ -888,10 +926,6 @@ msgstr "Sendt"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Indstil procentvise tærskler for målerfarver." msgstr "Indstil procentvise tærskler for målerfarver."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Sætter standardtidsintervallet for diagrammer når et system vises."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Gennemløb af {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Gennemløb af rodfilsystemet" msgstr "Gennemløb af rodfilsystemet"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Tidsformat"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Til email(s)" msgstr "Til email(s)"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Samlet modtaget data for hver interface"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Samlet sendt data for hver interface"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr "Oppe"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Upload"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Oppetid" msgstr "Oppetid"

View File

@@ -363,6 +363,14 @@ msgstr "Erstellt"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritisch (%)" msgstr "Kritisch (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativer Download"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativer Upload"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Offline"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Offline ({downSystemsLength})" msgstr "Offline ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Download"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Dauer" msgstr "Dauer"
@@ -452,6 +464,7 @@ msgstr "Bearbeiten"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-Mail" msgstr "E-Mail"
@@ -472,6 +485,10 @@ msgstr "E-Mail-Adresse eingeben, um das Passwort zurückzusetzen"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "E-Mail-Adresse eingeben..." msgstr "E-Mail-Adresse eingeben..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Geben Sie Ihr Einmalpasswort ein."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Für <0>{min}</0> {min, plural, one {Minute} other {Minuten}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Passwort vergessen?" msgstr "Passwort vergessen?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD Befehl"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Anzeige- und Benachrichtigungseinstellungen verwalten." msgstr "Anzeige- und Benachrichtigungseinstellungen verwalten."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Anleitung zur manuellen Einrichtung" msgstr "Anleitung zur manuellen Einrichtung"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Netzwerkverkehr der Docker-Container" msgstr "Netzwerkverkehr der Docker-Container"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Netzwerkverkehr der öffentlichen Schnittstellen" msgstr "Netzwerkverkehr der öffentlichen Schnittstellen"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC-Unterstützung"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Bei jedem Neustart werden die Systeme in der Datenbank aktualisiert, um den in der Datei definierten Systemen zu entsprechen." msgstr "Bei jedem Neustart werden die Systeme in der Datenbank aktualisiert, um den in der Datei definierten Systemen zu entsprechen."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Einmalpasswort"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lesen"
msgid "Received" msgid "Received"
msgstr "Empfangen" msgstr "Empfangen"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Einmalpasswort anfordern"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP anfordern"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Passwort zurücksetzen" msgstr "Passwort zurücksetzen"
@@ -888,10 +926,6 @@ msgstr "Gesendet"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Prozentuale Schwellenwerte für Zählerfarben festlegen." msgstr "Prozentuale Schwellenwerte für Zählerfarben festlegen."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Legt den Standardzeitraum für Diagramme fest, wenn ein System angezeigt wird."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Durchsatz von {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Durchsatz des Root-Dateisystems" msgstr "Durchsatz des Root-Dateisystems"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Zeitformat"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "An E-Mail(s)" msgstr "An E-Mail(s)"
@@ -1034,6 +1072,14 @@ msgstr "Tokens ermöglichen es Agents, sich zu verbinden und zu registrieren. Fi
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokens und Fingerabdrücke werden verwendet, um WebSocket-Verbindungen zum Hub zu authentifizieren." msgstr "Tokens und Fingerabdrücke werden verwendet, um WebSocket-Verbindungen zum Hub zu authentifizieren."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Gesamtdatenmenge für jede Schnittstelle empfangen"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Gesamtdatenmenge für jede Schnittstelle gesendet"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Löst aus, wenn der Lastdurchschnitt der letzten Minute einen Schwellenwert überschreitet" msgstr "Löst aus, wenn der Lastdurchschnitt der letzten Minute einen Schwellenwert überschreitet"
@@ -1095,6 +1141,10 @@ msgstr "aktiv"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "aktiv ({upSystemsLength})" msgstr "aktiv ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Upload"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Betriebszeit" msgstr "Betriebszeit"

View File

@@ -358,6 +358,14 @@ msgstr "Created"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Critical (%)" msgstr "Critical (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Cumulative Download"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Cumulative Upload"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -436,6 +444,10 @@ msgstr "Down"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Down ({downSystemsLength})" msgstr "Down ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Download"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Duration" msgstr "Duration"
@@ -447,6 +459,7 @@ msgstr "Edit"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -467,6 +480,10 @@ msgstr "Enter email address to reset password"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Enter email address..." msgstr "Enter email address..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Enter your one-time password."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -537,6 +554,12 @@ msgstr "For <0>{min}</0> {min, plural, one {minute} other {minutes}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Forgot password?" msgstr "Forgot password?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD command"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -640,6 +663,7 @@ msgid "Manage display and notification preferences."
msgstr "Manage display and notification preferences." msgstr "Manage display and notification preferences."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Manual setup instructions" msgstr "Manual setup instructions"
@@ -675,6 +699,8 @@ msgid "Network traffic of docker containers"
msgstr "Network traffic of docker containers" msgstr "Network traffic of docker containers"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Network traffic of public interfaces" msgstr "Network traffic of public interfaces"
@@ -710,6 +736,10 @@ msgstr "OAuth 2 / OIDC support"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "On each restart, systems in the database will be updated to match the systems defined in the file." msgstr "On each restart, systems in the database will be updated to match the systems defined in the file."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "One-time password"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -828,6 +858,14 @@ msgstr "Read"
msgid "Received" msgid "Received"
msgstr "Received" msgstr "Received"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Request a one-time password"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Request OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Reset Password" msgstr "Reset Password"
@@ -883,10 +921,6 @@ msgstr "Sent"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Set percentage thresholds for meter colors." msgstr "Set percentage thresholds for meter colors."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Sets the default time range for charts when a system is viewed."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -997,6 +1031,10 @@ msgstr "Throughput of {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Throughput of root filesystem" msgstr "Throughput of root filesystem"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Time format"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "To email(s)" msgstr "To email(s)"
@@ -1029,6 +1067,14 @@ msgstr "Tokens allow agents to connect and register. Fingerprints are stable ide
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgstr "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Total data received for each interface"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Total data sent for each interface"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Triggers when 1 minute load average exceeds a threshold" msgstr "Triggers when 1 minute load average exceeds a threshold"
@@ -1090,6 +1136,10 @@ msgstr "Up"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Up ({upSystemsLength})" msgstr "Up ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Upload"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Uptime" msgstr "Uptime"

View File

@@ -363,6 +363,14 @@ msgstr "Creado"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Crítico (%)" msgstr "Crítico (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Descarga acumulativa"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Carga acumulativa"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Abajo"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Abajo ({downSystemsLength})" msgstr "Abajo ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Descargar"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Duración" msgstr "Duración"
@@ -452,6 +464,7 @@ msgstr "Editar"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Correo electrónico" msgstr "Correo electrónico"
@@ -472,6 +485,10 @@ msgstr "Ingrese la dirección de correo electrónico para restablecer la contras
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Ingrese dirección de correo..." msgstr "Ingrese dirección de correo..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Ingrese su contraseña de un solo uso."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Por <0>{min}</0> {min, plural, one {minuto} other {minutos}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "¿Olvidó su contraseña?" msgstr "¿Olvidó su contraseña?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Comando FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Administrar preferencias de visualización y notificaciones." msgstr "Administrar preferencias de visualización y notificaciones."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Instrucciones manuales de configuración" msgstr "Instrucciones manuales de configuración"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Tráfico de red de los contenedores de Docker" msgstr "Tráfico de red de los contenedores de Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Tráfico de red de interfaces públicas" msgstr "Tráfico de red de interfaces públicas"
@@ -715,6 +741,10 @@ msgstr "Soporte para OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "En cada reinicio, los sistemas en la base de datos se actualizarán para coincidir con los sistemas definidos en el archivo." msgstr "En cada reinicio, los sistemas en la base de datos se actualizarán para coincidir con los sistemas definidos en el archivo."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Contraseña de un solo uso"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lectura"
msgid "Received" msgid "Received"
msgstr "Recibido" msgstr "Recibido"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Solicitar contraseña de un solo uso"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Solicitar OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Restablecer Contraseña" msgstr "Restablecer Contraseña"
@@ -888,10 +926,6 @@ msgstr "Enviado"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Establecer umbrales de porcentaje para los colores de los medidores." msgstr "Establecer umbrales de porcentaje para los colores de los medidores."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Establece el rango de tiempo predeterminado para los gráficos cuando se visualiza un sistema."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Rendimiento de {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Rendimiento del sistema de archivos raíz" msgstr "Rendimiento del sistema de archivos raíz"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Formato de hora"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "A correo(s)" msgstr "A correo(s)"
@@ -1034,6 +1072,14 @@ msgstr "Los tokens permiten que los agentes se conecten y registren. Las huellas
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Los tokens y las huellas digitales se utilizan para autenticar las conexiones WebSocket al hub." msgstr "Los tokens y las huellas digitales se utilizan para autenticar las conexiones WebSocket al hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Datos totales recibidos por cada interfaz"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Datos totales enviados por cada interfaz"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Se activa cuando la carga media de 1 minuto supera un umbral" msgstr "Se activa cuando la carga media de 1 minuto supera un umbral"
@@ -1095,6 +1141,10 @@ msgstr "Activo"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Activo ({upSystemsLength})" msgstr "Activo ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Cargar"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Tiempo de actividad" msgstr "Tiempo de actividad"

View File

@@ -363,6 +363,14 @@ msgstr "ایجاد شده"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "بحرانی (%)" msgstr "بحرانی (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "دانلود تجمعی"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "آپلود تجمعی"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "قطع"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "قطع ({downSystemsLength})" msgstr "قطع ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "دانلود"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "مدت زمان" msgstr "مدت زمان"
@@ -452,6 +464,7 @@ msgstr "ویرایش"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "ایمیل" msgstr "ایمیل"
@@ -472,6 +485,10 @@ msgstr "آدرس ایمیل را برای بازنشانی رمز عبور وا
msgid "Enter email address..." msgid "Enter email address..."
msgstr "آدرس ایمیل را وارد کنید..." msgstr "آدرس ایمیل را وارد کنید..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "رمز عبور یک‌بار مصرف خود را وارد کنید."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "برای <0>{min}</0> {min, plural, one {دقیقه} other {دقیقه}}
msgid "Forgot password?" msgid "Forgot password?"
msgstr "رمز عبور را فراموش کرده‌اید؟" msgstr "رمز عبور را فراموش کرده‌اید؟"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "دستور FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "مدیریت تنظیمات نمایش و اعلان‌ها." msgstr "مدیریت تنظیمات نمایش و اعلان‌ها."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "دستورالعمل‌های راه‌اندازی دستی" msgstr "دستورالعمل‌های راه‌اندازی دستی"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "ترافیک شبکه کانتینرهای داکر" msgstr "ترافیک شبکه کانتینرهای داکر"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "ترافیک شبکه رابط‌های عمومی" msgstr "ترافیک شبکه رابط‌های عمومی"
@@ -715,6 +741,10 @@ msgstr "پشتیبانی از OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "در هر بار راه‌اندازی مجدد، سیستم‌های موجود در پایگاه داده با سیستم‌های تعریف شده در فایل مطابقت داده می‌شوند." msgstr "در هر بار راه‌اندازی مجدد، سیستم‌های موجود در پایگاه داده با سیستم‌های تعریف شده در فایل مطابقت داده می‌شوند."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "رمز عبور یک‌بار مصرف"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "خواندن"
msgid "Received" msgid "Received"
msgstr "دریافت شد" msgstr "دریافت شد"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "درخواست رمز عبور یک‌بار مصرف"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "درخواست OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "بازنشانی رمز عبور" msgstr "بازنشانی رمز عبور"
@@ -888,10 +926,6 @@ msgstr "ارسال شد"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "آستانه های درصدی را برای رنگ های متر تنظیم کنید." msgstr "آستانه های درصدی را برای رنگ های متر تنظیم کنید."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "بازه زمانی پیش‌فرض برای نمودارها هنگام مشاهده یک سیستم را تعیین می‌کند."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "توان عملیاتی {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "توان عملیاتی سیستم فایل ریشه" msgstr "توان عملیاتی سیستم فایل ریشه"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "فرمت زمان"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "به ایمیل(ها)" msgstr "به ایمیل(ها)"
@@ -1034,6 +1072,14 @@ msgstr "توکن‌ها به عامل‌ها اجازه اتصال و ثبت‌
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "توکن‌ها و اثرات انگشت برای احراز هویت اتصالات WebSocket به هاب استفاده می‌شوند." msgstr "توکن‌ها و اثرات انگشت برای احراز هویت اتصالات WebSocket به هاب استفاده می‌شوند."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "داده‌های کل دریافت شده برای هر رابط"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "داده‌های کل ارسال شده برای هر رابط"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "هنگامی که میانگین بار ۱ دقیقه‌ای از یک آستانه فراتر رود، فعال می‌شود" msgstr "هنگامی که میانگین بار ۱ دقیقه‌ای از یک آستانه فراتر رود، فعال می‌شود"
@@ -1095,6 +1141,10 @@ msgstr "فعال"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "فعال ({upSystemsLength})" msgstr "فعال ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "آپلود"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "آپتایم" msgstr "آپتایم"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Critique (%)" msgstr "Critique (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Téléchargement cumulatif"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Téléversement cumulatif"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Injoignable"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Télécharger"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr "Éditer"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Entrez l'adresse email pour réinitialiser le mot de passe"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Entrez l'adresse email..." msgstr "Entrez l'adresse email..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Entrez votre mot de passe à usage unique."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Pour <0>{min}</0> {min, plural, one {minute} other {minutes}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Mot de passe oublié ?" msgstr "Mot de passe oublié ?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Commande FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Gérer les préférences d'affichage et de notification." msgstr "Gérer les préférences d'affichage et de notification."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Guide pour une installation manuelle" msgstr "Guide pour une installation manuelle"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Trafic réseau des conteneurs Docker" msgstr "Trafic réseau des conteneurs Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Trafic réseau des interfaces publiques" msgstr "Trafic réseau des interfaces publiques"
@@ -715,6 +741,10 @@ msgstr "Support OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "À chaque redémarrage, les systèmes dans la base de données seront mis à jour pour correspondre aux systèmes définis dans le fichier." msgstr "À chaque redémarrage, les systèmes dans la base de données seront mis à jour pour correspondre aux systèmes définis dans le fichier."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Mot de passe à usage unique"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lecture"
msgid "Received" msgid "Received"
msgstr "Reçu" msgstr "Reçu"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Demander un mot de passe à usage unique"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Demander OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Réinitialiser le mot de passe" msgstr "Réinitialiser le mot de passe"
@@ -888,10 +926,6 @@ msgstr "Envoyé"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Définir des seuils de pourcentage pour les couleurs des compteurs." msgstr "Définir des seuils de pourcentage pour les couleurs des compteurs."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Définit la plage de temps par défaut pour les graphiques lorsqu'un système est consulté."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Débit de {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Débit du système de fichiers racine" msgstr "Débit du système de fichiers racine"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Format d'heure"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Aux email(s)" msgstr "Aux email(s)"
@@ -1034,6 +1072,14 @@ msgstr "Les tokens permettent aux agents de se connecter et de s'enregistrer. Le
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Les tokens et les empreintes sont utilisés pour authentifier les connexions WebSocket vers le hub." msgstr "Les tokens et les empreintes sont utilisés pour authentifier les connexions WebSocket vers le hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Données totales reçues pour chaque interface"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Données totales envoyées pour chaque interface"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr "Joignable"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Téléverser"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Temps de fonctionnement" msgstr "Temps de fonctionnement"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritično (%)" msgstr "Kritično (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativno preuzimanje"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativno otpremanje"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr ""
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Preuzmi"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Unesite email adresu za resetiranje lozinke"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Unesite email adresu..." msgstr "Unesite email adresu..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Unesite Vašu jednokratnu lozinku."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Za <0>{min}</0> {min, plural, one {minutu} other {minute}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Zaboravljena lozinka?" msgstr "Zaboravljena lozinka?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD naredba"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Upravljajte postavkama prikaza i obavijesti." msgstr "Upravljajte postavkama prikaza i obavijesti."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "" msgstr ""
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Mrežni promet Docker spremnika" msgstr "Mrežni promet Docker spremnika"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Mrežni promet javnih sučelja" msgstr "Mrežni promet javnih sučelja"
@@ -715,6 +741,10 @@ msgstr "Podrška za OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Prilikom svakog ponovnog pokretanja, sustavi u bazi podataka biti će ažurirani kako bi odgovarali sustavima definiranim u datoteci." msgstr "Prilikom svakog ponovnog pokretanja, sustavi u bazi podataka biti će ažurirani kako bi odgovarali sustavima definiranim u datoteci."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Jednokratna lozinka"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Pročitaj"
msgid "Received" msgid "Received"
msgstr "Primljeno" msgstr "Primljeno"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Zatraži jednokratnu lozinku"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Zatraži OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Resetiraj Lozinku" msgstr "Resetiraj Lozinku"
@@ -888,10 +926,6 @@ msgstr "Poslano"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Postavite pragove postotka za boje mjerača." msgstr "Postavite pragove postotka za boje mjerača."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Postavlja zadani vremenski raspon za grafikone kada se sustav gleda."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Protok {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Protok root datotečnog sustava" msgstr "Protok root datotečnog sustava"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Format vremena"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Primaoci e-pošte" msgstr "Primaoci e-pošte"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Ukupni podaci primljeni za svako sučelje"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Ukupni podaci poslani za svako sučelje"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr ""
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Otpremi"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Vrijeme rada" msgstr "Vrijeme rada"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritikus (%)" msgstr "Kritikus (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulatív letöltés"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulatív feltöltés"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr ""
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Letöltés"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "E-mail cím megadása a jelszó visszaállításához"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Adja meg az e-mail címet..." msgstr "Adja meg az e-mail címet..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Adja meg az egyszeri jelszavát."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "A <0>{min}</0> {min, plural, one {perc} other {percek}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Elfelejtette a jelszavát?" msgstr "Elfelejtette a jelszavát?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD parancs"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "A megjelenítési és értesítési beállítások kezelése." msgstr "A megjelenítési és értesítési beállítások kezelése."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "" msgstr ""
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker konténerek hálózati forgalma" msgstr "Docker konténerek hálózati forgalma"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Nyilvános interfészek hálózati forgalma" msgstr "Nyilvános interfészek hálózati forgalma"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC támogatás"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Minden újraindításkor az adatbázisban lévő rendszerek frissítésre kerülnek, hogy megfeleljenek a fájlban meghatározott rendszereknek." msgstr "Minden újraindításkor az adatbázisban lévő rendszerek frissítésre kerülnek, hogy megfeleljenek a fájlban meghatározott rendszereknek."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Egyszeri jelszó"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Olvasás"
msgid "Received" msgid "Received"
msgstr "Fogadott" msgstr "Fogadott"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Egyszeri jelszó kérése"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP kérése"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Jelszó visszaállítása" msgstr "Jelszó visszaállítása"
@@ -888,10 +926,6 @@ msgstr "Elküldve"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Százalékos küszöbértékek beállítása a mérőszínekhez." msgstr "Százalékos küszöbértékek beállítása a mérőszínekhez."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Beállítja az alapértelmezett időtartamot a diagramokhoz, amikor egy rendszert néznek."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "A {extraFsName} átviteli teljesítménye"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "A gyökér fájlrendszer átviteli teljesítménye" msgstr "A gyökér fájlrendszer átviteli teljesítménye"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Időformátum"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "E-mailben" msgstr "E-mailben"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Összes fogadott adat minden interfészenként"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Összes elküldött adat minden interfészenként"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr ""
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Feltöltés"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Üzemidő" msgstr "Üzemidő"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritískt (%)" msgstr "Kritískt (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr ""
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr ""
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr ""
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Netfang" msgstr "Netfang"
@@ -472,6 +485,10 @@ msgstr "Settu netfang til að endursetja lykilorð"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Settu inn Netfang..." msgstr "Settu inn Netfang..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr ""
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Gleymt lykilorð?" msgstr "Gleymt lykilorð?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr ""
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "" msgstr ""
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "" msgstr ""
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Net traffík docker kerfa" msgstr "Net traffík docker kerfa"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "" msgstr ""
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC stuðningur"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "" msgstr ""
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr ""
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lesa"
msgid "Received" msgid "Received"
msgstr "Móttekið" msgstr "Móttekið"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr ""
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr ""
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Endurstilla lykilorð" msgstr "Endurstilla lykilorð"
@@ -888,10 +926,6 @@ msgstr "Sent"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Stilltu prósentuþröskuld fyrir mælaliti." msgstr "Stilltu prósentuþröskuld fyrir mælaliti."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr ""
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr ""
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "" msgstr ""
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr ""
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Til tölvupósta" msgstr "Til tölvupósta"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr ""
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr ""
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr ""
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "" msgstr ""

View File

@@ -363,6 +363,14 @@ msgstr "Creato"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Critico (%)" msgstr "Critico (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Download cumulativo"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Upload cumulativo"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Offline"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Offline ({downSystemsLength})" msgstr "Offline ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Scarica"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Durata" msgstr "Durata"
@@ -452,6 +464,7 @@ msgstr "Modifica"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Inserisci l'indirizzo email per reimpostare la password"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Inserisci l'indirizzo email..." msgstr "Inserisci l'indirizzo email..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Inserisci la tua password monouso."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Per <0>{min}</0> {min, plural, one {minuto} other {minuti}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Password dimenticata?" msgstr "Password dimenticata?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Comando FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Gestisci le preferenze di visualizzazione e notifica." msgstr "Gestisci le preferenze di visualizzazione e notifica."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Istruzioni di configurazione manuale" msgstr "Istruzioni di configurazione manuale"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Traffico di rete dei container Docker" msgstr "Traffico di rete dei container Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Traffico di rete delle interfacce pubbliche" msgstr "Traffico di rete delle interfacce pubbliche"
@@ -715,6 +741,10 @@ msgstr "Supporto OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Ad ogni riavvio, i sistemi nel database verranno aggiornati per corrispondere ai sistemi definiti nel file." msgstr "Ad ogni riavvio, i sistemi nel database verranno aggiornati per corrispondere ai sistemi definiti nel file."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Password monouso"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lettura"
msgid "Received" msgid "Received"
msgstr "Ricevuto" msgstr "Ricevuto"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Richiedi una password monouso"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Richiedi OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Reimposta Password" msgstr "Reimposta Password"
@@ -888,10 +926,6 @@ msgstr "Inviato"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Imposta le soglie percentuali per i colori dei contatori." msgstr "Imposta le soglie percentuali per i colori dei contatori."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Imposta l'intervallo di tempo predefinito per i grafici quando viene visualizzato un sistema."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Throughput di {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Throughput del filesystem root" msgstr "Throughput del filesystem root"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Formato orario"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "A email(s)" msgstr "A email(s)"
@@ -1034,6 +1072,14 @@ msgstr "I token consentono agli agenti di connettersi e registrarsi. Le impronte
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "I token e le impronte digitali vengono utilizzati per autenticare le connessioni WebSocket all'hub." msgstr "I token e le impronte digitali vengono utilizzati per autenticare le connessioni WebSocket all'hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Dati totali ricevuti per ogni interfaccia"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Dati totali inviati per ogni interfaccia"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Si attiva quando la media di carico di 1 minuto supera una soglia" msgstr "Si attiva quando la media di carico di 1 minuto supera una soglia"
@@ -1095,6 +1141,10 @@ msgstr "Attivo"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Attivo ({upSystemsLength})" msgstr "Attivo ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Carica"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Tempo di attività" msgstr "Tempo di attività"

View File

@@ -363,6 +363,14 @@ msgstr "作成日"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "致命的 (%)" msgstr "致命的 (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "累積ダウンロード"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "累積アップロード"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "停止"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "停止 ({downSystemsLength})" msgstr "停止 ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "ダウンロード"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "期間" msgstr "期間"
@@ -452,6 +464,7 @@ msgstr "編集"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "メール" msgstr "メール"
@@ -472,6 +485,10 @@ msgstr "パスワードをリセットするためにメールアドレスを入
msgid "Enter email address..." msgid "Enter email address..."
msgstr "メールアドレスを入力..." msgstr "メールアドレスを入力..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "ワンタイムパスワードを入力してください。"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "<0>{min}</0> {min, plural, one {分} other {分}}の間"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "パスワードをお忘れですか?" msgstr "パスワードをお忘れですか?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD コマンド"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "表示と通知の設定を管理します。" msgstr "表示と通知の設定を管理します。"
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "手動セットアップの手順" msgstr "手動セットアップの手順"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Dockerコンテナのネットワークトラフィック" msgstr "Dockerコンテナのネットワークトラフィック"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "パブリックインターフェースのネットワークトラフィック" msgstr "パブリックインターフェースのネットワークトラフィック"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDCサポート"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "再起動のたびに、データベース内のシステムはファイルに定義されたシステムに一致するように更新されます。" msgstr "再起動のたびに、データベース内のシステムはファイルに定義されたシステムに一致するように更新されます。"
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "ワンタイムパスワード"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "読み取り"
msgid "Received" msgid "Received"
msgstr "受信" msgstr "受信"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "ワンタイムパスワードをリクエスト"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP をリクエスト"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "パスワードをリセット" msgstr "パスワードをリセット"
@@ -888,10 +926,6 @@ msgstr "送信"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "メーターの色を変更するしきい値(パーセンテージ)を設定します。" msgstr "メーターの色を変更するしきい値(パーセンテージ)を設定します。"
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "システムを表示する際のチャートのデフォルトの時間範囲を設定します。"
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName}のスループット"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "ルートファイルシステムのスループット" msgstr "ルートファイルシステムのスループット"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "時間形式"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "宛先メールアドレス" msgstr "宛先メールアドレス"
@@ -1034,6 +1072,14 @@ msgstr "トークンはエージェントの接続と登録を可能にします
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "トークンとフィンガープリントは、ハブへのWebSocket接続の認証に使用されます。" msgstr "トークンとフィンガープリントは、ハブへのWebSocket接続の認証に使用されます。"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "各インターフェースの総受信データ量"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "各インターフェースの総送信データ量"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "1分間の負荷平均がしきい値を超えたときにトリガーされます" msgstr "1分間の負荷平均がしきい値を超えたときにトリガーされます"
@@ -1095,6 +1141,10 @@ msgstr "正常"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "正常 ({upSystemsLength})" msgstr "正常 ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "アップロード"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "稼働時間" msgstr "稼働時間"

View File

@@ -363,6 +363,14 @@ msgstr "생성됨"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "위험 (%)" msgstr "위험 (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "누적 다운로드"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "누적 업로드"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "오프라인"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "오프라인 ({downSystemsLength})" msgstr "오프라인 ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "다운로드"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "기간" msgstr "기간"
@@ -452,6 +464,7 @@ msgstr "수정"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "이메일" msgstr "이메일"
@@ -472,6 +485,10 @@ msgstr "비밀번호를 재설정하려면 이메일 주소를 입력하세요"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "이메일 주소 입력..." msgstr "이메일 주소 입력..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "일회용 비밀번호를 입력하세요."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "<0>{min}</0> {min, plural, one {분} other {분}} 동안"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "비밀번호를 잊으셨나요?" msgstr "비밀번호를 잊으셨나요?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD 명령어"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "디스플레이 및 알림 설정" msgstr "디스플레이 및 알림 설정"
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "수동 설정 방법" msgstr "수동 설정 방법"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker 컨테이너의 네트워크 트래픽" msgstr "Docker 컨테이너의 네트워크 트래픽"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "공용 인터페이스의 네트워크 트래픽" msgstr "공용 인터페이스의 네트워크 트래픽"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC 지원"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "매 시작 시, 데이터베이스가 파일에 정의된 시스템과 일치하도록 업데이트됩니다." msgstr "매 시작 시, 데이터베이스가 파일에 정의된 시스템과 일치하도록 업데이트됩니다."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "일회용 비밀번호"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "읽기"
msgid "Received" msgid "Received"
msgstr "수신됨" msgstr "수신됨"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "일회용 비밀번호 요청"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP 요청"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "비밀번호 재설정" msgstr "비밀번호 재설정"
@@ -888,10 +926,6 @@ msgstr "보냄"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "그래프 미터 색상의 백분율 임계값을 설정합니다." msgstr "그래프 미터 색상의 백분율 임계값을 설정합니다."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "시스템을 볼 때 차트의 기본 시간 범위를 설정합니다."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName}의 처리량"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "루트 파일 시스템의 처리량" msgstr "루트 파일 시스템의 처리량"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "시간 형식"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "받는사람(들)" msgstr "받는사람(들)"
@@ -1034,6 +1072,14 @@ msgstr "토큰은 에이전트가 연결하고 등록할 수 있도록 합니다
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "토큰과 지문은 허브에 대한 WebSocket 연결을 인증하는 데 사용됩니다." msgstr "토큰과 지문은 허브에 대한 WebSocket 연결을 인증하는 데 사용됩니다."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "각 인터페이스별 총 수신 데이터량"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "각 인터페이스별 총 발신 데이터량"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "1분 부하 평균이 임계값을 초과하면 트리거됩니다." msgstr "1분 부하 평균이 임계값을 초과하면 트리거됩니다."
@@ -1095,6 +1141,10 @@ msgstr "온라인"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "온라인 ({upSystemsLength})" msgstr "온라인 ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "업로드"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "가동 시간" msgstr "가동 시간"

View File

@@ -363,6 +363,14 @@ msgstr "Aangemaakt"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritiek (%)" msgstr "Kritiek (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Cumulatieve download"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Cumulatieve upload"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Offline"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Offline ({downSystemsLength})" msgstr "Offline ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Downloaden"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Duur" msgstr "Duur"
@@ -452,6 +464,7 @@ msgstr "Bewerken"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-mail" msgstr "E-mail"
@@ -472,6 +485,10 @@ msgstr "Voer een e-mailadres in om het wachtwoord opnieuw in te stellen"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Voer een e-mailadres in..." msgstr "Voer een e-mailadres in..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Voer uw eenmalig wachtwoord in."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Voor <0>{min}</0> {min, plural, one {minuut} other {minuten}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Wachtwoord vergeten?" msgstr "Wachtwoord vergeten?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD commando"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Weergave- en notificatievoorkeuren beheren." msgstr "Weergave- en notificatievoorkeuren beheren."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Handmatige installatie-instructies" msgstr "Handmatige installatie-instructies"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Netwerkverkeer van docker containers" msgstr "Netwerkverkeer van docker containers"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Netwerkverkeer van publieke interfaces" msgstr "Netwerkverkeer van publieke interfaces"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC ondersteuning"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Bij elke herstart zullen systemen in de database worden bijgewerkt om overeen te komen met de systemen die in het bestand zijn gedefinieerd." msgstr "Bij elke herstart zullen systemen in de database worden bijgewerkt om overeen te komen met de systemen die in het bestand zijn gedefinieerd."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Eenmalig wachtwoord"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lezen"
msgid "Received" msgid "Received"
msgstr "Ontvangen" msgstr "Ontvangen"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Eenmalig wachtwoord aanvragen"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP aanvragen"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Wachtwoord resetten" msgstr "Wachtwoord resetten"
@@ -888,10 +926,6 @@ msgstr "Verzonden"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Stel percentagedrempels in voor meterkleuren." msgstr "Stel percentagedrempels in voor meterkleuren."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Stelt het standaard tijdsbereik voor grafieken in wanneer een systeem wordt bekeken."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Doorvoer van {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Doorvoer van het root bestandssysteem" msgstr "Doorvoer van het root bestandssysteem"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Tijdnotatie"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Naar e-mail(s)" msgstr "Naar e-mail(s)"
@@ -1034,6 +1072,14 @@ msgstr "Tokens staan agenten toe om verbinding te maken met en te registreren. V
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokens en vingerafdrukken worden gebruikt om WebSocket verbindingen te verifiëren naar de hub." msgstr "Tokens en vingerafdrukken worden gebruikt om WebSocket verbindingen te verifiëren naar de hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Totaal ontvangen gegevens per interface"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Totaal verzonden gegevens per interface"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Triggert wanneer de gemiddelde belasting een drempelwaarde overschrijdt" msgstr "Triggert wanneer de gemiddelde belasting een drempelwaarde overschrijdt"
@@ -1095,6 +1141,10 @@ msgstr "Online"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Online ({upSystemsLength})" msgstr "Online ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Uploaden"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Actief" msgstr "Actief"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritisk (%)" msgstr "Kritisk (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativ nedlasting"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativ opplasting"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Nede"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Last ned"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr "Rediger"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-post" msgstr "E-post"
@@ -472,6 +485,10 @@ msgstr "Skriv inn e-postadresse for å nullstille passordet"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Skriv inn e-postadresse..." msgstr "Skriv inn e-postadresse..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Skriv inn ditt engangspassord."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "I <0>{min}</0> {min, plural, one {minutt} other {minutter}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Glemt passord?" msgstr "Glemt passord?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD kommando"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Endre visnings- og varslingsinnstillinger." msgstr "Endre visnings- og varslingsinnstillinger."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Instruks for Manuell Installasjon" msgstr "Instruks for Manuell Installasjon"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Nettverkstrafikk av docker-konteinere" msgstr "Nettverkstrafikk av docker-konteinere"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Nettverkstrafikk av eksterne nettverksgrensesnitt" msgstr "Nettverkstrafikk av eksterne nettverksgrensesnitt"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC-støtte"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Ved hver omstart vil systemer i databasen bli oppdatert til å matche systemene definert i fila." msgstr "Ved hver omstart vil systemer i databasen bli oppdatert til å matche systemene definert i fila."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Engangspassord"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Lesing"
msgid "Received" msgid "Received"
msgstr "Mottatt" msgstr "Mottatt"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Be om engangspassord"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Be om OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Nullstill Passord" msgstr "Nullstill Passord"
@@ -888,10 +926,6 @@ msgstr "Sendt"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Angi prosentvise terskler for målerfarger." msgstr "Angi prosentvise terskler for målerfarger."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Angir standard tidsperiode for diagrammer når et system vises."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Gjennomstrømning av {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Gjennomstrømning av rot-filsystemet" msgstr "Gjennomstrømning av rot-filsystemet"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Tidsformat"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Til e-postadresse(r)" msgstr "Til e-postadresse(r)"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Totalt mottatt data for hvert grensesnitt"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Totalt sendt data for hvert grensesnitt"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr "Oppe"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Last opp"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Oppetid" msgstr "Oppetid"

View File

@@ -363,6 +363,14 @@ msgstr "Utworzono"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Krytyczny (%)" msgstr "Krytyczny (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Pobieranie skumulowane"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Wysyłanie skumulowane"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Nie działa"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Nie działa ({downSystemsLength})" msgstr "Nie działa ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Pobierz"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Czas trwania" msgstr "Czas trwania"
@@ -452,6 +464,7 @@ msgstr "Edytuj"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-mail" msgstr "E-mail"
@@ -472,6 +485,10 @@ msgstr "Wprowadź adres e-mail, aby zresetować hasło"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Wprowadź adres e-mail..." msgstr "Wprowadź adres e-mail..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Wprowadź swoje jednorazowe hasło."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Na <0>{min}</0> {min, plural, one {minutę} other {minut}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Zapomniałeś hasła?" msgstr "Zapomniałeś hasła?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Polecenie FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Zarządzaj preferencjami wyświetlania i powiadomień." msgstr "Zarządzaj preferencjami wyświetlania i powiadomień."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Instrukcja ręcznej konfiguracji" msgstr "Instrukcja ręcznej konfiguracji"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Ruch sieciowy kontenerów Docker." msgstr "Ruch sieciowy kontenerów Docker."
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Ruch sieciowy interfejsów publicznych" msgstr "Ruch sieciowy interfejsów publicznych"
@@ -715,6 +741,10 @@ msgstr "Wsparcie OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Przy każdym ponownym uruchomieniu systemy w bazie danych będą aktualizowane, aby odpowiadały systemom zdefiniowanym w pliku." msgstr "Przy każdym ponownym uruchomieniu systemy w bazie danych będą aktualizowane, aby odpowiadały systemom zdefiniowanym w pliku."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Hasło jednorazowe"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Czytaj"
msgid "Received" msgid "Received"
msgstr "Otrzymane" msgstr "Otrzymane"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Zażądaj jednorazowego hasła"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Zażądaj OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Resetuj hasło" msgstr "Resetuj hasło"
@@ -888,10 +926,6 @@ msgstr "Wysłane"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Ustaw progi procentowe dla kolorów mierników." msgstr "Ustaw progi procentowe dla kolorów mierników."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Ustawia domyślny zakres czasowy dla wykresów, gdy system jest wyświetlony."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Przepustowość {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Przepustowość głównego systemu plików" msgstr "Przepustowość głównego systemu plików"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Format czasu"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Do e-mail(ów)" msgstr "Do e-mail(ów)"
@@ -1034,6 +1072,14 @@ msgstr "Tokeny umożliwiają agentom łączenie się i rejestrację. Odciski pal
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokeny i odciski palców (fingerprinty) służą do uwierzytelniania połączeń WebSocket z hubem." msgstr "Tokeny i odciski palców (fingerprinty) służą do uwierzytelniania połączeń WebSocket z hubem."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Całkowita ilość danych odebranych dla każdego interfejsu"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Całkowita ilość danych wysłanych dla każdego interfejsu"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Uruchamia się, gdy 1-minutowe średnie obciążenie systemu przekroczy ustawiony próg" msgstr "Uruchamia się, gdy 1-minutowe średnie obciążenie systemu przekroczy ustawiony próg"
@@ -1095,6 +1141,10 @@ msgstr "Działa"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Działa ({upSystemsLength})" msgstr "Działa ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Wyślij"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Czas pracy" msgstr "Czas pracy"

View File

@@ -363,6 +363,14 @@ msgstr "Criado"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Crítico (%)" msgstr "Crítico (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Download cumulativo"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Upload cumulativo"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "“Desligado”"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Inativo ({downSystemsLength})" msgstr "Inativo ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Transferir"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Duração" msgstr "Duração"
@@ -452,6 +464,7 @@ msgstr "Editar"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Digite o endereço de email para redefinir a senha"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Digite o endereço de email..." msgstr "Digite o endereço de email..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Insira a sua senha de uso único."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Por <0>{min}</0> {min, plural, one {minuto} other {minutos}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Esqueceu a senha?" msgstr "Esqueceu a senha?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Comando FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Gerenciar preferências de exibição e notificação." msgstr "Gerenciar preferências de exibição e notificação."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Instruções de configuração manual" msgstr "Instruções de configuração manual"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Tráfego de rede dos contêineres Docker" msgstr "Tráfego de rede dos contêineres Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Tráfego de rede das interfaces públicas" msgstr "Tráfego de rede das interfaces públicas"
@@ -715,6 +741,10 @@ msgstr "Suporte a OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "A cada reinício, os sistemas no banco de dados serão atualizados para corresponder aos sistemas definidos no arquivo." msgstr "A cada reinício, os sistemas no banco de dados serão atualizados para corresponder aos sistemas definidos no arquivo."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Senha de uso único"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Ler"
msgid "Received" msgid "Received"
msgstr "Recebido" msgstr "Recebido"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Solicitar senha de uso único"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Solicitar OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Redefinir Senha" msgstr "Redefinir Senha"
@@ -888,10 +926,6 @@ msgstr "Enviado"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Defina os limiares de porcentagem para as cores do medidor." msgstr "Defina os limiares de porcentagem para as cores do medidor."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Define o intervalo de tempo padrão para gráficos quando um sistema é visualizado."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Taxa de transferência de {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Taxa de transferência do sistema de arquivos raiz" msgstr "Taxa de transferência do sistema de arquivos raiz"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Formato de hora"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Para email(s)" msgstr "Para email(s)"
@@ -1034,6 +1072,14 @@ msgstr "Os tokens permitem que os agentes se conectem e registrem. As impressõe
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Tokens e impressões digitais são usados para autenticar conexões WebSocket ao hub." msgstr "Tokens e impressões digitais são usados para autenticar conexões WebSocket ao hub."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Dados totais recebidos para cada interface"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Dados totais enviados para cada interface"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Dispara quando a média de carga de 1 minuto excede um limite" msgstr "Dispara quando a média de carga de 1 minuto excede um limite"
@@ -1095,6 +1141,10 @@ msgstr "“Ligado”"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Ativo ({upSystemsLength})" msgstr "Ativo ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Carregar"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Tempo de Atividade" msgstr "Tempo de Atividade"

View File

@@ -363,6 +363,14 @@ msgstr "Создано"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Критический (%)" msgstr "Критический (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Совокупная загрузка"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Совокупная выгрузка"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Не в сети"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Скачать"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Длительность" msgstr "Длительность"
@@ -452,6 +464,7 @@ msgstr "Редактировать"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Электронная почта" msgstr "Электронная почта"
@@ -472,6 +485,10 @@ msgstr "Введите адрес электронной почты для сб
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Введите адрес электронной почты..." msgstr "Введите адрес электронной почты..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Введите ваш одноразовый пароль."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "На <0>{min}</0> {min, plural, one {минуту} other {минут}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Забыли пароль?" msgstr "Забыли пароль?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Команда FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Управляйте предпочтениями отображения и уведомлений." msgstr "Управляйте предпочтениями отображения и уведомлений."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Инструкции по ручной настройке" msgstr "Инструкции по ручной настройке"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Сетевой трафик контейнеров Docker" msgstr "Сетевой трафик контейнеров Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Сетевой трафик публичных интерфейсов" msgstr "Сетевой трафик публичных интерфейсов"
@@ -715,6 +741,10 @@ msgstr "Поддержка OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "При каждом перезапуске системы в базе данных будут обновлены в соответствии с системами, определенными в файле." msgstr "При каждом перезапуске системы в базе данных будут обновлены в соответствии с системами, определенными в файле."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Одноразовый пароль"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Чтение"
msgid "Received" msgid "Received"
msgstr "Получено" msgstr "Получено"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Запросить одноразовый пароль"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Запросить OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Сбросить пароль" msgstr "Сбросить пароль"
@@ -888,10 +926,6 @@ msgstr "Отправлено"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Установите процентные пороги для цветов счетчиков." msgstr "Установите процентные пороги для цветов счетчиков."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Устанавливает диапазон времени по умолчанию для графиков при просмотре системы."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Пропускная способность {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Пропускная способность корневой файловой системы" msgstr "Пропускная способность корневой файловой системы"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Формат времени"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "На электронную почту" msgstr "На электронную почту"
@@ -1034,6 +1072,14 @@ msgstr "Токены позволяют агентам подключаться
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Токены и отпечатки используются для аутентификации соединений WebSocket с хабом." msgstr "Токены и отпечатки используются для аутентификации соединений WebSocket с хабом."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Общий объем полученных данных для каждого интерфейса"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Общий объем отправленных данных для каждого интерфейса"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Срабатывает, когда средняя загрузка за 1 минуту превышает порог" msgstr "Срабатывает, когда средняя загрузка за 1 минуту превышает порог"
@@ -1095,6 +1141,10 @@ msgstr "В сети"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Загрузить"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Время работы" msgstr "Время работы"

View File

@@ -363,6 +363,14 @@ msgstr ""
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritično (%)" msgstr "Kritično (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativno prenos"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativno nalaganje"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr ""
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Prenesi"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-pošta" msgstr "E-pošta"
@@ -472,6 +485,10 @@ msgstr "Vnesite e-poštni naslov za ponastavitev gesla"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Vnesite e-poštni naslov..." msgstr "Vnesite e-poštni naslov..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Vnesite svoje enkratno geslo."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Za <0>{min}</0> {min, plural, one {minuto} other {minut}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Pozabljeno geslo?" msgstr "Pozabljeno geslo?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Ukaz FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Upravljajte nastavitve prikaza in obvestil." msgstr "Upravljajte nastavitve prikaza in obvestil."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "" msgstr ""
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Omrežni promet docker kontejnerjev" msgstr "Omrežni promet docker kontejnerjev"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Omrežni promet javnih vmesnikov" msgstr "Omrežni promet javnih vmesnikov"
@@ -715,6 +741,10 @@ msgstr "Podpora za OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Ob vsakem ponovnem zagonu bodo sistemi v zbirki podatkov posodobljeni, da se bodo ujemali s sistemi, definiranimi v datoteki." msgstr "Ob vsakem ponovnem zagonu bodo sistemi v zbirki podatkov posodobljeni, da se bodo ujemali s sistemi, definiranimi v datoteki."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Enkratno geslo"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Preberano"
msgid "Received" msgid "Received"
msgstr "Prejeto" msgstr "Prejeto"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Zahtevaj enkratno geslo"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Zahtevaj OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Ponastavi geslo" msgstr "Ponastavi geslo"
@@ -888,10 +926,6 @@ msgstr "Poslano"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Nastavite odstotne pragove za barve merilnikov." msgstr "Nastavite odstotne pragove za barve merilnikov."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Nastavi privzeti časovni obseg za grafikone, ko si ogledujete sistem."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Prepustnost {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Prepustnost korenskega datotečnega sistema" msgstr "Prepustnost korenskega datotečnega sistema"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Oblika časa"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "E-pošta za" msgstr "E-pošta za"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Skupni prejeti podatki za vsak vmesnik"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Skupni poslani podatki za vsak vmesnik"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr ""
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Naloži"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Čas delovanja" msgstr "Čas delovanja"

View File

@@ -363,6 +363,14 @@ msgstr "Skapad"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritisk (%)" msgstr "Kritisk (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kumulativ nedladdning"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kumulativ uppladdning"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr ""
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Ladda ner"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "" msgstr ""
@@ -452,6 +464,7 @@ msgstr ""
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-post" msgstr "E-post"
@@ -472,6 +485,10 @@ msgstr "Ange e-postadress för att återställa lösenord"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Ange e-postadress..." msgstr "Ange e-postadress..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Ange ditt engångslösenord."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Under <0>{min}</0> {min, plural, one {minut} other {minuter}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Glömt lösenordet?" msgstr "Glömt lösenordet?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD kommando"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Hantera visnings- och aviseringsinställningar." msgstr "Hantera visnings- och aviseringsinställningar."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "" msgstr ""
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Nätverkstrafik för dockercontainrar" msgstr "Nätverkstrafik för dockercontainrar"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Nätverkstrafik för publika gränssnitt" msgstr "Nätverkstrafik för publika gränssnitt"
@@ -715,6 +741,10 @@ msgstr "Stöd för OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Vid varje omstart kommer systemen i databasen att uppdateras för att matcha systemen som definieras i filen." msgstr "Vid varje omstart kommer systemen i databasen att uppdateras för att matcha systemen som definieras i filen."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Engångslösenord"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Läs"
msgid "Received" msgid "Received"
msgstr "Mottaget" msgstr "Mottaget"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Begär engångslösenord"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Begär OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Återställ lösenord" msgstr "Återställ lösenord"
@@ -888,10 +926,6 @@ msgstr "Skickat"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Ställ in procentuella tröskelvärden för mätarfärger." msgstr "Ställ in procentuella tröskelvärden för mätarfärger."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Anger standardtidsintervallet för diagram när ett system visas."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Genomströmning av {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Genomströmning av rotfilsystemet" msgstr "Genomströmning av rotfilsystemet"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Tidsformat"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Till e-postadress(er)" msgstr "Till e-postadress(er)"
@@ -1034,6 +1072,14 @@ msgstr ""
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Totalt mottagen data för varje gränssnitt"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Totalt skickad data för varje gränssnitt"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "" msgstr ""
@@ -1095,6 +1141,10 @@ msgstr ""
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "" msgstr ""
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Ladda upp"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Drifttid" msgstr "Drifttid"

View File

@@ -363,6 +363,14 @@ msgstr "Oluşturuldu"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Kritik (%)" msgstr "Kritik (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Kümülatif İndirme"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Kümülatif Yükleme"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Kapalı"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Kapalı ({downSystemsLength})" msgstr "Kapalı ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "İndir"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Süre" msgstr "Süre"
@@ -452,6 +464,7 @@ msgstr "Düzenle"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "E-posta" msgstr "E-posta"
@@ -472,6 +485,10 @@ msgstr "Şifreyi sıfırlamak için e-posta adresini girin"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "E-posta adresini girin..." msgstr "E-posta adresini girin..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Tek kullanımlık şifrenizi girin."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "<0>{min}</0> {min, plural, one {dakika} other {dakika}} için"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Şifrenizi mi unuttunuz?" msgstr "Şifrenizi mi unuttunuz?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD komutu"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Görüntüleme ve bildirim tercihlerini yönetin." msgstr "Görüntüleme ve bildirim tercihlerini yönetin."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Manuel kurulum talimatları" msgstr "Manuel kurulum talimatları"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker konteynerlerinin ağ trafiği" msgstr "Docker konteynerlerinin ağ trafiği"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Genel arayüzlerin ağ trafiği" msgstr "Genel arayüzlerin ağ trafiği"
@@ -715,6 +741,10 @@ msgstr "OAuth 2 / OIDC desteği"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Her yeniden başlatmada, veritabanındaki sistemler dosyada tanımlanan sistemlerle eşleşecek şekilde güncellenecektir." msgstr "Her yeniden başlatmada, veritabanındaki sistemler dosyada tanımlanan sistemlerle eşleşecek şekilde güncellenecektir."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Tek kullanımlık şifre"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Oku"
msgid "Received" msgid "Received"
msgstr "Alındı" msgstr "Alındı"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Tek kullanımlık şifre iste"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "OTP iste"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Şifreyi Sıfırla" msgstr "Şifreyi Sıfırla"
@@ -888,10 +926,6 @@ msgstr "Gönderildi"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Sayaç renkleri için yüzde eşiklerini ayarlayın." msgstr "Sayaç renkleri için yüzde eşiklerini ayarlayın."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Bir sistem görüntülendiğinde grafikler için varsayılan zaman aralığını ayarlar."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName} verimliliği"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Kök dosya sisteminin verimliliği" msgstr "Kök dosya sisteminin verimliliği"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Zaman formatı"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "E-posta(lar)a" msgstr "E-posta(lar)a"
@@ -1034,6 +1072,14 @@ msgstr "Token'lar agentların bağlanıp kaydolmasına izin verir. Parmak izleri
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Token'lar ve parmak izleri hub'a WebSocket bağlantılarını doğrulamak için kullanılır." msgstr "Token'lar ve parmak izleri hub'a WebSocket bağlantılarını doğrulamak için kullanılır."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Her arayüz için alınan toplam veri"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Her arayüz için gönderilen toplam veri"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "1 dakikalık yük ortalaması bir eşiği aştığında tetiklenir" msgstr "1 dakikalık yük ortalaması bir eşiği aştığında tetiklenir"
@@ -1095,6 +1141,10 @@ msgstr "Açık"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Açık ({upSystemsLength})" msgstr "Açık ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Yükle"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Çalışma Süresi" msgstr "Çalışma Süresi"

View File

@@ -363,6 +363,14 @@ msgstr "Створено"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Критично (%)" msgstr "Критично (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Кумулятивне завантаження"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Кумулятивне відвантаження"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Не працює"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Не працює ({downSystemsLength})" msgstr "Не працює ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Завантажити"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Тривалість" msgstr "Тривалість"
@@ -452,6 +464,7 @@ msgstr "Редагувати"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Електронна пошта" msgstr "Електронна пошта"
@@ -472,6 +485,10 @@ msgstr "Введіть адресу електронної пошти для с
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Введіть адресу електронної пошти..." msgstr "Введіть адресу електронної пошти..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Введіть ваш одноразовий пароль."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Протягом <0>{min}</0> {min, plural, one {хвилини} other {
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Забули пароль?" msgstr "Забули пароль?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Команда FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Керуйте параметрами відображення та сповіщень." msgstr "Керуйте параметрами відображення та сповіщень."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Інструкції з ручного налаштування" msgstr "Інструкції з ручного налаштування"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Мережевий трафік контейнерів Docker" msgstr "Мережевий трафік контейнерів Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Мережевий трафік публічних інтерфейсів" msgstr "Мережевий трафік публічних інтерфейсів"
@@ -715,6 +741,10 @@ msgstr "Підтримка OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "При кожному перезапуску системи в базі даних будуть оновлені, щоб відповідати системам, визначеним у файлі." msgstr "При кожному перезапуску системи в базі даних будуть оновлені, щоб відповідати системам, визначеним у файлі."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Одноразовий пароль"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Читання"
msgid "Received" msgid "Received"
msgstr "Отримано" msgstr "Отримано"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Запит одноразового пароля"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Запит OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Скинути пароль" msgstr "Скинути пароль"
@@ -888,10 +926,6 @@ msgstr "Відправлено"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Встановіть відсоткові пороги для кольорів лічильників." msgstr "Встановіть відсоткові пороги для кольорів лічильників."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Встановлює стандартний діапазон часу для графіків при перегляді системи."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Пропускна здатність {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Пропускна здатність кореневої файлової системи" msgstr "Пропускна здатність кореневої файлової системи"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Формат часу"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "На електронну пошту" msgstr "На електронну пошту"
@@ -1034,6 +1072,14 @@ msgstr "Токени дозволяють агентам підключатис
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Токени та відбитки використовуються для автентифікації WebSocket з'єднань до хабу." msgstr "Токени та відбитки використовуються для автентифікації WebSocket з'єднань до хабу."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Загальний обсяг отриманих даних для кожного інтерфейсу"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Загальний обсяг відправлених даних для кожного інтерфейсу"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Спрацьовує, коли середнє навантаження за 1 хвилину перевищує поріг" msgstr "Спрацьовує, коли середнє навантаження за 1 хвилину перевищує поріг"
@@ -1095,6 +1141,10 @@ msgstr "Працює"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Працює ({upSystemsLength})" msgstr "Працює ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Відвантажити"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Час роботи" msgstr "Час роботи"

View File

@@ -363,6 +363,14 @@ msgstr "Đã tạo"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "Độ nghiêm trọng (%)" msgstr "Độ nghiêm trọng (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "Tải xuống tích lũy"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "Tải lên tích lũy"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "Mất kết nối"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "Mất kết nối ({downSystemsLength})" msgstr "Mất kết nối ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "Tải xuống"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "Thời lượng" msgstr "Thời lượng"
@@ -452,6 +464,7 @@ msgstr "Chỉnh sửa"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "Email" msgstr "Email"
@@ -472,6 +485,10 @@ msgstr "Nhập địa chỉ email để đặt lại mật khẩu"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "Nhập địa chỉ email..." msgstr "Nhập địa chỉ email..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "Nhập mật khẩu một lần của bạn."
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "Trong <0>{min}</0> {min, plural, one {phút} other {phút}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "Quên mật khẩu?" msgstr "Quên mật khẩu?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "Lệnh FreeBSD"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "Quản lý tùy chọn hiển thị và thông báo." msgstr "Quản lý tùy chọn hiển thị và thông báo."
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "Hướng dẫn cài đặt thủ công" msgstr "Hướng dẫn cài đặt thủ công"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Lưu lượng mạng của các container Docker" msgstr "Lưu lượng mạng của các container Docker"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "Lưu lượng mạng của các giao diện công cộng" msgstr "Lưu lượng mạng của các giao diện công cộng"
@@ -715,6 +741,10 @@ msgstr "Hỗ trợ OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "Mỗi khi khởi động lại, các hệ thống trong cơ sở dữ liệu sẽ được cập nhật để khớp với các hệ thống được định nghĩa trong tệp." msgstr "Mỗi khi khởi động lại, các hệ thống trong cơ sở dữ liệu sẽ được cập nhật để khớp với các hệ thống được định nghĩa trong tệp."
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "Mật khẩu một lần"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "Đọc"
msgid "Received" msgid "Received"
msgstr "Đã nhận" msgstr "Đã nhận"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "Yêu cầu mật khẩu một lần"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "Yêu cầu OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "Đặt lại Mật khẩu" msgstr "Đặt lại Mật khẩu"
@@ -888,10 +926,6 @@ msgstr "Đã gửi"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "Đặt ngưỡng cho màu sắc đồng hồ." msgstr "Đặt ngưỡng cho màu sắc đồng hồ."
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "Đặt phạm vi thời gian mặc định cho biểu đồ khi một hệ thống được xem."
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "Thông lượng của {extraFsName}"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Thông lượng của hệ thống tệp gốc" msgstr "Thông lượng của hệ thống tệp gốc"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "Định dạng thời gian"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "Đến email(s)" msgstr "Đến email(s)"
@@ -1034,6 +1072,14 @@ msgstr "Token cho phép các tác nhân kết nối và đăng ký. Vân tay là
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "Token và vân tay được sử dụng để xác thực các kết nối WebSocket đến trung tâm." msgstr "Token và vân tay được sử dụng để xác thực các kết nối WebSocket đến trung tâm."
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "Tổng dữ liệu nhận được cho mỗi giao diện"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "Tổng dữ liệu gửi đi cho mỗi giao diện"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "Kích hoạt khi tải trung bình 1 phút vượt quá ngưỡng" msgstr "Kích hoạt khi tải trung bình 1 phút vượt quá ngưỡng"
@@ -1095,6 +1141,10 @@ msgstr "Hoạt động"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "Hoạt động ({upSystemsLength})" msgstr "Hoạt động ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "Tải lên"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "Thời gian hoạt động" msgstr "Thời gian hoạt động"

View File

@@ -363,6 +363,14 @@ msgstr "创建时间"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "临界 (%)" msgstr "临界 (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "累计下载"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "累计上传"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "离线"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "离线 ({downSystemsLength})" msgstr "离线 ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "下载"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "持续时间" msgstr "持续时间"
@@ -452,6 +464,7 @@ msgstr "编辑"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "电子邮件" msgstr "电子邮件"
@@ -472,6 +485,10 @@ msgstr "输入电子邮件地址以重置密码"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "输入电子邮件地址..." msgstr "输入电子邮件地址..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "输入您的一次性密码。"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "持续<0>{min}</0> {min, plural, one {分钟} other {分钟}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "忘记密码?" msgstr "忘记密码?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD 命令"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "管理显示和通知偏好。" msgstr "管理显示和通知偏好。"
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "手动设置说明" msgstr "手动设置说明"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker 容器的网络流量" msgstr "Docker 容器的网络流量"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "公共接口的网络流量" msgstr "公共接口的网络流量"
@@ -715,6 +741,10 @@ msgstr "支持 OAuth 2/OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "每次重启时,数据库中的系统将更新以匹配文件中定义的系统。" msgstr "每次重启时,数据库中的系统将更新以匹配文件中定义的系统。"
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "一次性密码"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "读取"
msgid "Received" msgid "Received"
msgstr "接收" msgstr "接收"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "请求一次性密码"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "请求 OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "重置密码" msgstr "重置密码"
@@ -888,10 +926,6 @@ msgstr "发送"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "设置仪表颜色的百分比阈值。" msgstr "设置仪表颜色的百分比阈值。"
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "设置查看系统时图表的默认时间范围。"
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName}的吞吐量"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "根文件系统的吞吐量" msgstr "根文件系统的吞吐量"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "时间格式"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "发送到电子邮件" msgstr "发送到电子邮件"
@@ -1034,6 +1072,14 @@ msgstr "令牌允许客户端连接和注册。指纹是每个系统唯一的稳
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "令牌与指纹用于验证到中心的 WebSocket 连接。" msgstr "令牌与指纹用于验证到中心的 WebSocket 连接。"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "每个接口的总接收数据量"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "每个接口的总发送数据量"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "当 1 分钟负载平均值超过阈值时触发" msgstr "当 1 分钟负载平均值超过阈值时触发"
@@ -1095,6 +1141,10 @@ msgstr "在线"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "在线 ({upSystemsLength})" msgstr "在线 ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "上传"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "正常运行时间" msgstr "正常运行时间"

View File

@@ -363,6 +363,14 @@ msgstr "已建立"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "嚴重 (%)" msgstr "嚴重 (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "累計下載"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "累計上傳"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "中斷"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "中斷 ({downSystemsLength})" msgstr "中斷 ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "下載"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "持續時間" msgstr "持續時間"
@@ -452,6 +464,7 @@ msgstr "編輯"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "電子郵件" msgstr "電子郵件"
@@ -472,6 +485,10 @@ msgstr "輸入電子郵件地址以重置密碼"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "輸入電子郵件地址..." msgstr "輸入電子郵件地址..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "輸入您的一次性密碼。"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "持續<0>{min}</0> {min, plural, one {分鐘} other {分鐘}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "忘記密碼?" msgstr "忘記密碼?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD 指令"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "管理顯示和通知偏好。" msgstr "管理顯示和通知偏好。"
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "手動設定說明" msgstr "手動設定說明"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker 容器的網絡流量" msgstr "Docker 容器的網絡流量"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "公共接口的網絡流量" msgstr "公共接口的網絡流量"
@@ -715,6 +741,10 @@ msgstr "支援 OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "每次重新啟動時,將會以檔案中的系統定義更新資料庫。" msgstr "每次重新啟動時,將會以檔案中的系統定義更新資料庫。"
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "一次性密碼"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "讀取"
msgid "Received" msgid "Received"
msgstr "接收" msgstr "接收"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "請求一次性密碼"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "請求 OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "重設密碼" msgstr "重設密碼"
@@ -888,10 +926,6 @@ msgstr "發送"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "設定儀表顏色的百分比閾值。" msgstr "設定儀表顏色的百分比閾值。"
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "設置查看系統時圖表的默認時間範圍。"
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName}的吞吐量"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "根文件系統的吞吐量" msgstr "根文件系統的吞吐量"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "時間格式"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "發送到電子郵件" msgstr "發送到電子郵件"
@@ -1034,6 +1072,14 @@ msgstr "令牌允許代理程式連接和註冊。指紋是每個系統唯一的
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "令牌和指紋用於驗證到中心的WebSocket連接。" msgstr "令牌和指紋用於驗證到中心的WebSocket連接。"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "每個介面的總接收資料量"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "每個介面的總傳送資料量"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "當 1 分鐘平均負載超過閾值時觸發" msgstr "當 1 分鐘平均負載超過閾值時觸發"
@@ -1095,6 +1141,10 @@ msgstr "上線"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "上線 ({upSystemsLength})" msgstr "上線 ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "上傳"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "正常運行時間" msgstr "正常運行時間"

View File

@@ -363,6 +363,14 @@ msgstr "已建立"
msgid "Critical (%)" msgid "Critical (%)"
msgstr "嚴重 (%)" msgstr "嚴重 (%)"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Download"
msgstr "累計下載"
#: src/components/routes/system/network-sheet.tsx
msgid "Cumulative Upload"
msgstr "累計上傳"
#. Context: Battery state #. Context: Battery state
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Current state" msgid "Current state"
@@ -441,6 +449,10 @@ msgstr "離線"
msgid "Down ({downSystemsLength})" msgid "Down ({downSystemsLength})"
msgstr "離線 ({downSystemsLength})" msgstr "離線 ({downSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Download"
msgstr "下載"
#: src/components/alerts-history-columns.tsx #: src/components/alerts-history-columns.tsx
msgid "Duration" msgid "Duration"
msgstr "持續時間" msgstr "持續時間"
@@ -452,6 +464,7 @@ msgstr "編輯"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
#: src/components/login/otp-forms.tsx
msgid "Email" msgid "Email"
msgstr "電子郵件" msgstr "電子郵件"
@@ -472,6 +485,10 @@ msgstr "輸入電子郵件地址以重設密碼"
msgid "Enter email address..." msgid "Enter email address..."
msgstr "輸入電子郵件地址..." msgstr "輸入電子郵件地址..."
#: src/components/login/otp-forms.tsx
msgid "Enter your one-time password."
msgstr "輸入您的一次性密碼。"
#: src/components/login/auth-form.tsx #: src/components/login/auth-form.tsx
#: src/components/routes/settings/alerts-history-data-table.tsx #: src/components/routes/settings/alerts-history-data-table.tsx
#: src/components/routes/settings/config-yaml.tsx #: src/components/routes/settings/config-yaml.tsx
@@ -542,6 +559,12 @@ msgstr "持續<0>{min}</0> {min, plural, one {分鐘} other {分鐘}}"
msgid "Forgot password?" msgid "Forgot password?"
msgstr "忘記密碼?" msgstr "忘記密碼?"
#: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgctxt "Button to copy install command"
msgid "FreeBSD command"
msgstr "FreeBSD 指令"
#. Context: Battery state #. Context: Battery state
#: src/lib/i18n.ts #: src/lib/i18n.ts
msgid "Full" msgid "Full"
@@ -645,6 +668,7 @@ msgid "Manage display and notification preferences."
msgstr "管理顯示和通知偏好。" msgstr "管理顯示和通知偏好。"
#: src/components/add-system.tsx #: src/components/add-system.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx
msgid "Manual setup instructions" msgid "Manual setup instructions"
msgstr "手動設定說明" msgstr "手動設定說明"
@@ -680,6 +704,8 @@ msgid "Network traffic of docker containers"
msgstr "Docker 容器的網路流量" msgstr "Docker 容器的網路流量"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
#: src/components/routes/system/network-sheet.tsx
#: src/components/routes/system/network-sheet.tsx
msgid "Network traffic of public interfaces" msgid "Network traffic of public interfaces"
msgstr "公開介面的網路流量" msgstr "公開介面的網路流量"
@@ -715,6 +741,10 @@ msgstr "支援 OAuth 2 / OIDC"
msgid "On each restart, systems in the database will be updated to match the systems defined in the file." msgid "On each restart, systems in the database will be updated to match the systems defined in the file."
msgstr "每次重新啟動時,將會以檔案中的系統定義更新資料庫。" msgstr "每次重新啟動時,將會以檔案中的系統定義更新資料庫。"
#: src/components/login/auth-form.tsx
msgid "One-time password"
msgstr "一次性密碼"
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/routes/settings/tokens-fingerprints.tsx #: src/components/routes/settings/tokens-fingerprints.tsx
#: src/components/systems-table/systems-table-columns.tsx #: src/components/systems-table/systems-table-columns.tsx
@@ -833,6 +863,14 @@ msgstr "讀取"
msgid "Received" msgid "Received"
msgstr "接收" msgstr "接收"
#: src/components/login/login.tsx
msgid "Request a one-time password"
msgstr "請求一次性密碼"
#: src/components/login/otp-forms.tsx
msgid "Request OTP"
msgstr "請求 OTP"
#: src/components/login/forgot-pass-form.tsx #: src/components/login/forgot-pass-form.tsx
msgid "Reset Password" msgid "Reset Password"
msgstr "重設密碼" msgstr "重設密碼"
@@ -888,10 +926,6 @@ msgstr "傳送"
msgid "Set percentage thresholds for meter colors." msgid "Set percentage thresholds for meter colors."
msgstr "設定儀表顏色的百分比閾值。" msgstr "設定儀表顏色的百分比閾值。"
#: src/components/routes/settings/general.tsx
msgid "Sets the default time range for charts when a system is viewed."
msgstr "設定顯示系統圖表的預設時間範圍。"
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/command-palette.tsx #: src/components/command-palette.tsx
#: src/components/routes/settings/layout.tsx #: src/components/routes/settings/layout.tsx
@@ -1002,6 +1036,10 @@ msgstr "{extraFsName}的傳輸速率"
msgid "Throughput of root filesystem" msgid "Throughput of root filesystem"
msgstr "Root文件系統的傳輸速率" msgstr "Root文件系統的傳輸速率"
#: src/components/routes/settings/general.tsx
msgid "Time format"
msgstr "時間格式"
#: src/components/routes/settings/notifications.tsx #: src/components/routes/settings/notifications.tsx
msgid "To email(s)" msgid "To email(s)"
msgstr "發送到電子郵件" msgstr "發送到電子郵件"
@@ -1034,6 +1072,14 @@ msgstr "令牌允許代理程式連線和註冊。指紋是每個系統的唯一
msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub." msgid "Tokens and fingerprints are used to authenticate WebSocket connections to the hub."
msgstr "令牌和指紋被用於驗證到 Hub 的 WebSocket 連線。" msgstr "令牌和指紋被用於驗證到 Hub 的 WebSocket 連線。"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data received for each interface"
msgstr "每個介面的總接收資料量"
#: src/components/routes/system/network-sheet.tsx
msgid "Total data sent for each interface"
msgstr "每個介面的總傳送資料量"
#: src/lib/alerts.ts #: src/lib/alerts.ts
msgid "Triggers when 1 minute load average exceeds a threshold" msgid "Triggers when 1 minute load average exceeds a threshold"
msgstr "當 1 分鐘平均負載超過閾值時觸發" msgstr "當 1 分鐘平均負載超過閾值時觸發"
@@ -1095,6 +1141,10 @@ msgstr "上線"
msgid "Up ({upSystemsLength})" msgid "Up ({upSystemsLength})"
msgstr "上線 ({upSystemsLength})" msgstr "上線 ({upSystemsLength})"
#: src/components/routes/system/network-sheet.tsx
msgid "Upload"
msgstr "上傳"
#: src/components/routes/system.tsx #: src/components/routes/system.tsx
msgid "Uptime" msgid "Uptime"
msgstr "運行時間" msgstr "運行時間"

View File

@@ -141,6 +141,8 @@ export interface SystemStats {
g?: Record<string, GPUData> g?: Record<string, GPUData>
/** battery percent and state */ /** battery percent and state */
bat?: [number, BatteryState] bat?: [number, BatteryState]
/** network interfaces [upload bytes, download bytes, total upload bytes, total download bytes] */
ni?: Record<string, [number, number, number, number]>
} }
export interface GPUData { export interface GPUData {

View File

View File

@@ -125,3 +125,28 @@ func CreateSystems(app core.App, count int, userId string, status string) ([]*co
} }
return systems, nil return systems, nil
} }
// GetHubWithUser creates a test hub with a test user and user settings
func GetHubWithUser(t *testing.T) (*TestHub, *core.Record) {
hub, err := NewTestHub(t.TempDir())
assert.NoError(t, err)
hub.StartHub()
// Manually initialize the system manager to bind event hooks
err = hub.GetSystemManager().Initialize()
assert.NoError(t, err)
// Create a test user
user, err := CreateUser(hub, "test@example.com", "password")
assert.NoError(t, err)
// Create user settings for the test user (required for alert notifications)
userSettingsData := map[string]any{
"user": user.Id,
"settings": `{"emails":[test@example.com],"webhooks":[]}`,
}
_, err = CreateRecord(hub, "user_settings", userSettingsData)
assert.NoError(t, err)
return hub, user
}

View File

@@ -1,5 +1,14 @@
## 0.12.9
- Fix divide by zero error introduced in 0.12.8 :) (#1175)
## 0.12.8 ## 0.12.8
- Add per-interface network traffic charts. (#926)
- Add cumulative network traffic charts. (#926)
- Add setting for time format (12h / 24h). (#424) - Add setting for time format (12h / 24h). (#424)
- Add experimental one-time password (OTP) support. - Add experimental one-time password (OTP) support.
@@ -10,6 +19,8 @@
- Add FreeBSD support for agent install script and update command. - Add FreeBSD support for agent install script and update command.
- Fix status alerts not being resolved when system comes up. (#1052)
## 0.12.7 ## 0.12.7
- Make LibreHardwareMonitor opt-in with `LHM=true` environment variable. (#1130) - Make LibreHardwareMonitor opt-in with `LHM=true` environment variable. (#1130)