3

I need to get the currently logged in user(s) on the local Windows machine, using Golang. I'm not looking for the user currently running the application, which can be got from the built-in function user.Current().

I can call query user from cmd and this gives me the list (string manipulation required, but that is not a problem) of users I need.

The code I have tried is:

out, err := exec.Command("query", "user")
if err != nil {
  panic(err)
}
// ...do something with 'out'

This produces the error panic: exit status 1. The same occurs if I do:

out, err := exec.Command("cmd", "/C", "query", "user")
...
bcvery1
  • 198
  • 1
  • 13

2 Answers2

1

As usually with such kind of questions, the solution is to proceed like this:

  1. Research (using MSDN and other sources) on how to achieve the stated goal using Win32 API.
  2. Use the built-in syscall package (or, if available/desirable, helper 3rd-party packages) to make those calls from Go.

The first step can be this which yields the solution which basically is "use WTS".

The way to go is to

  1. Connect to the WTS subsystem¹.
  2. Enumerate the currently active sessions.
  3. Query each one for the information about the identity of the user associated with it.

The second step is trickier but basically you'd need to research how others do that. See this and this and this for a few examples.

You might also look at files named _windows*.go in the Go source of the syscall package.


¹ Note that even on a single-user machine, everything related to seat/session management comes through WTS (however castrated it is depending on a particular flavor of Windows). This is true since at least XP/W2k3.

kostix
  • 51,517
  • 14
  • 93
  • 176
0
package main

import (
    "fmt"
    "os/exec"
)


func main() {
    out, err := exec.Command("cmd", "/C", "query user").Output()
    if err != nil {
        fmt.Println("Error: ", err)
    }
    
    fmt.Println(string(out))
}
Dificilcoder
  • 449
  • 5
  • 11