代码之家  ›  专栏  ›  技术社区  ›  Chris Higg

如何从批处理文件以系统用户身份运行时访问用户%APPDATA%

  •  1
  • Chris Higg  · 技术社区  · 6 年前

    通过SCCM部署应用程序。目前正在尝试部署Wireshark,我首先尝试创建目录,然后将首选项文件复制给用户 %APPDATA% 。首选项文件基本上阻止应用程序检查自动更新。

    我需要创建目录的原因是,直到Wireshark第一次启动时,目录才存在。

    问题是,在执行此操作时,SCCM将作为系统用户进行部署,所以 %APPDATA% 转到目录 C:\Windows\System32\config\systemprofile\AppData\Roaming\

    但我想访问C:\Users\SPECIFIC USER\AppData\Roaming

    我正在使用批处理文件部署应用程序:


    Wireshark-win64-2.4.6.exe /S
    
    mkdir %APPDATA%\Wireshark\
    
    xcopy preferences %APPDATA%\Wireshark
    

    这将在我自己的机器上本地工作,但如果我在PSEXEC下运行(就像SCCM一样),那么它将最终位于错误的目录中。

    我不熟悉在SCCM中创建应用程序以及使用批处理文件进行部署,因此请尽可能提供详细信息。不管怎样,我感谢你的帮助!

    4 回复  |  直到 6 年前
        1
  •  2
  •   michael_heath    6 年前

    使用完成 getprofiles.cmd 要回显配置文件,请使用 main.cmd 使用for循环处理轮廓路径。

    主要的cmd命令 :

    @echo off
    setlocal
    
    :: Install Wireshark.
    echo Wireshark-win64-2.4.6.exe /S
    
    :: Update Wireshark app data in user profiles.
    for /f "tokens=*" %%A in ('getprofiles.cmd "\AppData\Roaming"') do (
        call :skip_profile "%%~A" "\\Administrator\\" "\\MSSQL\$SQLEXPRESS\\" || (
            echo mkdir "%%~A\Wireshark\"
            echo xcopy preferences "%%~A\Wireshark"
        )
    )
    
    exit /b
    
    :skip_profile
    for %%A in (%*) do (
        if not "%%~A" == "" if /i not "%%~A" == "%~1" (
            echo "%~1"| findstr /i "%%~A" >nul 2>nul
            if not errorlevel 1 (
                echo Skip account "%~1"
                exit /b 0
            )
        )
    )
    exit /b 1
    

    获取配置文件。cmd命令 :

    @echo off
    setlocal
    
    if "%~1" == "/?" goto :help
    
    :: ProfileList key that contains profile paths.
    set "ProfileListKey=HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\ProfileList"
    
    :: Get profiles directory path.
    set "ProfilesDirectory="
    
    for /f "tokens=1,3" %%A in (
        'reg query "%ProfileListKey%" /v "ProfilesDirectory"'
    ) do if /i "%%~A" == "ProfilesDirectory" call set "ProfilesDirectory=%%~B"
    
    if not defined ProfilesDirectory (
        >&2 echo ProfilesDirectory is undefined
        exit /b 1
    )
    
    :: Search all profile paths in profiles directory and echo existing paths appended with the 1st script argument.
    for /f "delims=" %%A in (
        'reg query "%ProfileListKey%"'
    ) do call :ProfilePath "%%~A" "%~1"
    
    exit /b
    
    :ProfilePath
    setlocal
    set "arg1=%~1"
    
    :: Validate 1st call argument is a profile subkey.
    if not defined arg1 exit /b 1
    if /i "%arg1%" == "%ProfileListKey%" exit /b 1
    if "%arg1:~,1%" == " " exit /b 1
    
    :: Echo existing profile paths with defined 2nd argument appended.
    for /f "tokens=1,3" %%A in (
        'reg query "%arg1%" /v ProfileImagePath^|find /i "%ProfilesDirectory%"'
    ) do (
        if "%%~A" == "ProfileImagePath" (
            if exist "%%~B%~2" echo "%%~B%~2"
        )
    )
    exit /b
    
    :help
    echo Prints profile paths from the registry that exist in the Profiles Directory.
    echo 1st argument can be a path to be appended to the profile path.
    echo   i.e. "\AppData\Roaming" is appended to become "C:\Users\...\AppData\Roaming".
    exit /b
    

    剧本 主要的cmd命令 回显测试结果。消除回声 如果命令有效,则实际使用。

    这个 ProfileList 注册表中的键存储查找 配置文件,并具有子键,其中包含数据,例如上每个配置文件的路径 机器。

    主要的cmd命令 可以避免配置文件,例如 Administrator MSSQL$SQLEXPRESS 。 被叫标签 :skip_profile 将概要文件路径作为第一个参数。 以下参数用于模式,如果匹配,将跳过 轮廓 findstr 用于检查配置文件路径是否与匹配 正则表达式如此使用 findstr /? 语法要求。 大小写设置为不区分使用 /i

    这个 获取配置文件。cmd命令 脚本获取 ProfilesDirectory 路径,其中 是可以找到用户配置文件文件夹的位置。然后查询密钥 使用调用的标签获取配置文件键 :ProfilePath 。 标签检查 档案目录 路径位于每个 找到配置文件路径。然后在回音之前检查路径是否存在 路径。如果传递了可选的第一个参数,则 追加,路径将被验证为该路径。

    A测试输出:

    Wireshark-win64-2.4.6.exe /S
    mkdir "C:\Users\Michael\AppData\Roaming\Wireshark\"
    xcopy preferences "C:\Users\Michael\AppData\Roaming\Wireshark"
    

    这似乎还可以,因为我在当前机器上只有1个用户配置文件。

    不过,您可以将代码合并在一起,只生成一个脚本 我决定离开 获取配置文件。cmd命令 可重复用于其他用途。

        2
  •  0
  •   Christopher Maynard    6 年前

    这里有一个批处理文件,可以帮助您。它在所有用户的 %APPDATA% 如果未指定用户名或仅在特定用户的 %APPDATA% 如果指定用户名,则返回目录。

    @ECHO OFF
    SETLOCAL
    SETLOCAL ENABLEEXTENSIONS
    SETLOCAL ENABLEDELAYEDEXPANSION
    
    SET BAT=%~NX0
    SET ROOTDIR=C:\Users
    
    IF "%~1" == "" (
        GOTO USAGE
    )
    SET "DIR=%~1"
    SET "USER=%~2"
    IF NOT "%USER%" == "" (
        IF EXIST %ROOTDIR%\%USER%\AppData\Roaming\ (
            IF NOT EXIST "%ROOTDIR%\%USER%\AppData\Roaming\%DIR%" (
                MKDIR "%ROOTDIR%\%USER%\AppData\Roaming\%DIR%"
                ECHO Created %ROOTDIR%\%USER%\AppData\Roaming\%DIR%
            )
        )
        GOTO :EOF
    )
    
    FOR /F "DELIMS=" %%D IN ('DIR /A:D /B %ROOTDIR%') DO (
        IF EXIST %ROOTDIR%\%%D\AppData\Roaming\ (
            IF NOT EXIST "%ROOTDIR%\%%D\AppData\Roaming\%DIR%" (
                MKDIR "%ROOTDIR%\%%D\AppData\Roaming\%DIR%"
                ECHO Created %ROOTDIR%\%%D\AppData\Roaming\%DIR%
            )
        )
    )
    GOTO :EOF
    
    :: --------------------------------------------------------------------------
    :USAGE
    ECHO.
    ECHO   A batch file that creates a directory in every user's %%APPDATA%% directory
    ECHO   if no username is specified or creates the directory only for the specific
    ECHO   user if the username is specified.
    ECHO.
    ECHO   Usage: %BAT% ^<directory^> [username]
    GOTO :EOF
    
        3
  •  0
  •   VBScab    3 年前

    查找资源管理器的所有者。EXE进程:

    for /f "TOKENS=1,2,*" %%a in ('tasklist /FI "IMAGENAME eq explorer.exe" /FO LIST /V') do if /i "%%a %%b"=="User Name:" (set domain_user=%%c)
    
    for /f "TOKENS=1,2 DELIMS=\" %%a in ("%domain_user%") do set domain=%%a && set LoggedInUserID=%%b
    

        4
  •  0
  •   COYPER    3 年前

    对于/f“令牌=1,2,*”('tasklist/FI“IMAGENAME eq explorer.exe”/FO LIST/V)中的%%a,如果/i“%%a%%b”=“用户名:”(设置domain\u User=%%c),则执行该操作

    对于/f“TOKENS=1,2 DELIMS=”(“%domain\u user%”)中的%%a,请设置域=%%a(&&设置LoggedInUserID=%b