github.com/netdata/go.d.plugin@v0.58.1/modules/logind/collect.go (about) 1 // SPDX-License-Identifier: GPL-3.0-or-later 2 3 //go:build linux 4 // +build linux 5 6 package logind 7 8 import ( 9 "strings" 10 ) 11 12 func (l *Logind) collect() (map[string]int64, error) { 13 if l.conn == nil { 14 conn, err := l.newLogindConn(l.Config) 15 if err != nil { 16 return nil, err 17 } 18 l.conn = conn 19 } 20 21 mx := make(map[string]int64) 22 23 // https://www.freedesktop.org/wiki/Software/systemd/logind/ (Session Objects) 24 if err := l.collectSessions(mx); err != nil { 25 return nil, err 26 } 27 // https://www.freedesktop.org/wiki/Software/systemd/logind/ (User Objects) 28 if err := l.collectUsers(mx); err != nil { 29 return nil, err 30 } 31 32 return mx, nil 33 } 34 35 func (l *Logind) collectSessions(mx map[string]int64) error { 36 sessions, err := l.conn.ListSessions() 37 if err != nil { 38 return err 39 } 40 41 mx["sessions_remote"] = 0 42 mx["sessions_local"] = 0 43 mx["sessions_type_graphical"] = 0 44 mx["sessions_type_console"] = 0 45 mx["sessions_type_other"] = 0 46 mx["sessions_state_online"] = 0 47 mx["sessions_state_active"] = 0 48 mx["sessions_state_closing"] = 0 49 50 for _, session := range sessions { 51 props, err := l.conn.GetSessionProperties(session.Path) 52 if err != nil { 53 return err 54 } 55 56 if v, ok := props["Remote"]; ok && v.String() == "true" { 57 mx["sessions_remote"]++ 58 } else { 59 mx["sessions_local"]++ 60 } 61 62 if v, ok := props["Type"]; ok { 63 typ := strings.Trim(v.String(), "\"") 64 switch typ { 65 case "x11", "mir", "wayland": 66 mx["sessions_type_graphical"]++ 67 case "tty": 68 mx["sessions_type_console"]++ 69 case "unspecified": 70 mx["sessions_type_other"]++ 71 default: 72 l.Debugf("unknown session type '%s' for session '%s/%s'", typ, session.User, session.ID) 73 mx["sessions_type_other"]++ 74 } 75 } 76 77 if v, ok := props["State"]; ok { 78 state := strings.Trim(v.String(), "\"") 79 switch state { 80 case "online": 81 mx["sessions_state_online"]++ 82 case "active": 83 mx["sessions_state_active"]++ 84 case "closing": 85 mx["sessions_state_closing"]++ 86 default: 87 l.Debugf("unknown session state '%s' for session '%s/%s'", state, session.User, session.ID) 88 } 89 } 90 } 91 return nil 92 } 93 94 func (l *Logind) collectUsers(mx map[string]int64) error { 95 users, err := l.conn.ListUsers() 96 if err != nil { 97 return err 98 } 99 100 // https://www.freedesktop.org/software/systemd/man/sd_uid_get_state.html 101 mx["users_state_offline"] = 0 102 mx["users_state_lingering"] = 0 103 mx["users_state_online"] = 0 104 mx["users_state_active"] = 0 105 mx["users_state_closing"] = 0 106 107 for _, user := range users { 108 v, err := l.conn.GetUserProperty(user.Path, "State") 109 if err != nil { 110 return err 111 } 112 113 state := strings.Trim(v.String(), "\"") 114 switch state { 115 case "offline": 116 mx["users_state_offline"]++ 117 case "lingering": 118 mx["users_state_lingering"]++ 119 case "online": 120 mx["users_state_online"]++ 121 case "active": 122 mx["users_state_active"]++ 123 case "closing": 124 mx["users_state_closing"]++ 125 default: 126 l.Debugf("unknown user state '%s' for user '%s/%d'", state, user.Name, user.UID) 127 } 128 } 129 return nil 130 }