如何使用Go在Windows上请求管理员权限

pye*_*yed 14 windows go

我要实现我的应用程序是什么,是不是需要右键单击并选择以管理员身份运行我要运行它每次.我希望Windows提示我获得管理员权限,就像其他Windows应用程序一样.

考虑以下代码:

package main

import (
    "fmt"
    "io/ioutil"
    "time"
)

func main() {
    err := ioutil.WriteFile("C:/Windows/test.txt", []byte("TESTING!"), 0644)
    if err != nil {
        fmt.Println(err.Error())
        time.Sleep(time.Second * 3)
    }
}
Run Code Online (Sandbox Code Playgroud)

如果您编译它并双击它将打印:

open:C:\ Windows\test.txt:访问被拒绝.

但是,如果右键单击并以管理员身份运行,它将创建并写入该文件.

如何通过双击来询问管理员权限?

Col*_*son 15

您需要嵌入一个清单文件,告诉Windows您需要提升权限.

该页面的示例是:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
<assemblyIdentity
    version="9.0.0.0"
    processorArchitecture="x86"
    name="myapp.exe"
    type="win32"
/>
<description>My App</description>
<trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
    <security>
        <requestedPrivileges>
            <requestedExecutionLevel level="requireAdministrator" uiAccess="false"/>
        </requestedPrivileges>
    </security>
</trustInfo>
</assembly>
Run Code Online (Sandbox Code Playgroud)

这个疯狂的帖子表明使用rsrc应该为你做的伎俩.


jer*_*ack 14

这是我用来检测我是否以管理员身份运行的技术,如果没有使用 UAC 提示重新启动自己。这允许我在大多数情况下作为标准用户运行,并且仅在需要时提升。我在大多数功能不需要管理员权限的命令行工具中使用它,但像 -install 或 -uninstall 这样的功能可以,因为它们正在注册表或程序文件中写入 HKLM。这种方法不需要清单。

package main

import (
    "fmt"
    "golang.org/x/sys/windows"
    "os"
    "syscall"
    "time"
)

func main() {
    // if not elevated, relaunch by shellexecute with runas verb set
    if !amAdmin() {
        runMeElevated()
    }
    time.Sleep(10*time.Second)

}

func runMeElevated() {
    verb := "runas"
    exe, _ := os.Executable()
    cwd, _ := os.Getwd()
    args := strings.Join(os.Args[1:], " ")

    verbPtr, _ := syscall.UTF16PtrFromString(verb)
    exePtr, _ := syscall.UTF16PtrFromString(exe)
    cwdPtr, _ := syscall.UTF16PtrFromString(cwd)
    argPtr, _ := syscall.UTF16PtrFromString(args)

    var showCmd int32 = 1 //SW_NORMAL

    err := windows.ShellExecute(0, verbPtr, exePtr, argPtr, cwdPtr, showCmd)
    if err != nil {
        fmt.Println(err)
    }
}

func amAdmin() bool {
    _, err := os.Open("\\\\.\\PHYSICALDRIVE0")
    if err != nil {
        fmt.Println("admin no")
        return false
    }
    fmt.Println("admin yes")
    return true
}
Run Code Online (Sandbox Code Playgroud)

此处提供更多详细信息:https :
//gist.github.com/jerblack/d0eb182cc5a1c1d92d92a4c4fcc416c6