标题: [文本处理] 批处理修改ini文件中指定节点的键值 [打印本页]
作者: 670422423 时间: 2023-7-28 17:12 标题: 批处理修改ini文件中指定节点的键值
本帖最后由 670422423 于 2023-7-28 17:57 编辑
[SERVER_DATA_1]
SERVER_USER=123
SERVER_PASSWORD=123
[SERVER_DATA_2]
SERVER_USER=456
SERVER_PASSWORD=456
文件内容,文件格式为.ini,需要修改的内容如上示例,需要修改[SERVER_DATA_2]节点下SERVER_USER,SERVER_PASSWORD的值,并且文件所在路径中有空格“D:\Program Files (x86)\”
求大佬帮忙,报酬您说。
系统为win7
作者: zaqmlp 时间: 2023-7-28 17:53
¥20,bat存为ANSI/GB2312编码- <# :
- cls&echo off&cd /d "%~dp0"&set "current=%cd%"
- path %SYSTEMROOT%\System32\WindowsPowerShell\v1.0;%path%
- powershell -NoProfile -ExecutionPolicy bypass "Get-Content -literal \"%~f0\"|Out-String|Invoke-Expression"
- pause
- exit
- #>
- $inifile="D:\Program Files (x86)\xxx.ini";
- if(-not (test-path -literal $inifile)){write-host ('"'+$inifile+'" path error or not exist');exit;}
-
- $codes=@'
- using System;
- using System.Runtime.InteropServices;
- public static class EditINI
- {
- [DllImport("kernel32")]
- public static extern long WritePrivateProfileString(string section, string key, string val, string filePath);
- }
- '@;
- Add-Type -TypeDefinition $codes;
-
- [EditINI]::WritePrivateProfileString('SERVER_DATA_2', 'SERVER_USER', '112233', $inifile);
- [EditINI]::WritePrivateProfileString('SERVER_DATA_2', 'SERVER_PASSWORD', '88888', $inifile);
复制代码
作者: Batcher 时间: 2023-7-28 17:58
回复 1# 670422423
请参考Q-04和Q-05把bat文件和ini文件都保存为ANSI编码:
https://mp.weixin.qq.com/s/Koje4FufWxWBs7ioDy_LJA
不保留空行.bat- @echo off
- cd /d "%~dp0"
- setlocal enabledelayedexpansion
- set "FileOld=1.ini"
- set "FileNew=2.ini"
- set "BeginChange="
- (for /f "tokens=1,2 delims==" %%a in ('type "%FileOld%"') do (
- if "%%b" equ "" (
- set "ThisRow=%%a"
- ) else (
- set "ThisRow=%%a=%%b"
- )
- if "%%a" equ "[SERVER_DATA_2]" (
- echo,!ThisRow!
- set "BeginChange=true"
- ) else if "!BeginChange!" equ "true" (
- if "%%a" equ "SERVER_USER" (
- echo,%%a=bbs.bathome.net
- set "ChangeU=true"
- ) else if "%%a" equ "SERVER_PASSWORD" (
- echo,%%a=www.bathome.net
- set "ChangeP=true"
- ) else (
- echo,!ThisRow!
- )
- if "!ChangeU!" equ "true" (
- if "!ChangeP!" equ "true" (
- set "BeginChange=false"
- )
- )
- ) else (
- echo,!ThisRow!
- )
- ))>"%FileNew%"
复制代码
保留空行.bat- @echo off
- cd /d "%~dp0"
- setlocal enabledelayedexpansion
- set "FileOld=1.ini"
- set "FileNew=2.ini"
- set "BeginChange="
- (for /f "tokens=1,2 delims=:" %%i in ('findstr /n .* "%FileOld%"') do (
- if "%%j" equ "" (
- echo,
- ) else (
- for /f "tokens=1,2 delims==" %%a in ("%%j") do (
- if "%%b" equ "" (
- set "ThisRow=%%a"
- ) else (
- set "ThisRow=%%a=%%b"
- )
- if "%%a" equ "[SERVER_DATA_2]" (
- echo,!ThisRow!
- set "BeginChange=true"
- ) else if "!BeginChange!" equ "true" (
- if "%%a" equ "SERVER_USER" (
- echo,%%a=bbs.bathome.net
- set "ChangeU=true"
- ) else if "%%a" equ "SERVER_PASSWORD" (
- echo,%%a=www.bathome.net
- set "ChangeP=true"
- ) else (
- echo,!ThisRow!
- )
- if "!ChangeU!" equ "true" (
- if "!ChangeP!" equ "true" (
- set "BeginChange=false"
- )
- )
- ) else (
- echo,!ThisRow!
- )
- )
- )
- ))>"%FileNew%"
复制代码
批处理读取ini文件内容并修改指定的值
http://bbs.bathome.net/thread-30373-1-1.html
批处理读取ini文件指定小节的内容
http://bbs.bathome.net/thread-57942-1-1.html
作者: 670422423 时间: 2023-7-28 20:31
回复 2# zaqmlp
不能用
作者: 670422423 时间: 2023-7-28 21:17
回复 3# Batcher
可以在原文件上修改,不生成新的ini文件吗
作者: 670422423 时间: 2023-7-28 21:27
回复 670422423
请参考Q-04和Q-05把bat文件和ini文件都保存为ANSI编码:
批处理读取ini文件内容并修改 ...
Batcher 发表于 2023-7-28 17:58
实测可以修改,并生成新的ini文件,但是与原文件不太一样 好像把中间空行删除了。
作者: Batcher 时间: 2023-7-29 14:02
回复 5# 670422423
最后加一行:- move /y "%FileNew%" "%FileOld%"
复制代码
作者: CrLf 时间: 2023-7-29 16:43
用第三方工具inifile比较容易实现,可以到这里下载:http://bcn.bathome.net/s/tool/index.html?key=inifile
然后执行:- inifile a.ini [SERVER_DATA_2] SERVER_USER=123456
- inifile a.ini [SERVER_DATA_2] SERVER_PASSWORD=888888
复制代码
作者: hfxiang 时间: 2023-7-30 18:44
回复 6# 670422423
可尝试第3方工具sed( http://bcn.bathome.net/tool/4.8/sed.exe )- sed -r -i "/^\[SERVER_DATA_2\]$/,/^\[.*$/{s/^SERVER_USER=.*$/SERVER_USER=ABCDEFG/;s/^SERVER_PASSWORD=.*$/SERVER_PASSWORD=abcdefg/}" "D:\Program Files (x86)\1.txt"
复制代码
作者: wh7288 时间: 2023-7-31 08:40
本帖最后由 wh7288 于 2023-7-31 08:55 编辑
- set "LocalDir=D:\Program Files(x86)\111.ini"
- set "NewDir=D:\Program Files(x86)\111.ini.txt"
-
- setlocal enabledelayedexpansion
-
- if exist "%LocalDir%" (
-
- for /f "delims=" %%i in ('findstr /N .* %LocalDir%') do (
-
- set "str=%%i"
- set "str=!str:*:=!"
-
- if "!str!" equ "SERVER_USER=456" (
-
- echo SERVER_USER=XXXXXX
-
- ) else if "!str!" equ "SERVER_PASSWORD=456"(
-
- echo SERVER_PASSWORD=XXXXXX
-
- ) else (
-
- echo.!str!
- )
- )>>%NewDir%
- )
-
- endlocal
-
- echo F|xcopy /c /r /y %NewDir% %LocalDir%
-
- del /q %NewDir%
-
- pause
复制代码
作者: wh7288 时间: 2023-7-31 08:44
回复 2# zaqmlp
弱弱的问一句:大佬,这是bat代码吗?
作者: Batcher 时间: 2023-7-31 10:26
回复 10# wh7288
这代码是不行的。
1、不同的节点下面可能存在相同的用户名和密码
2、不能在代码里面把用户名和密码写死
作者: 77七 时间: 2023-7-31 11:37
本帖最后由 77七 于 2023-8-2 14:09 编辑
- @echo off
- (for /f "tokens=1* delims=:" %%a in ('findstr /n .* "1.ini"') do (
- if defined m (
- (for /f "tokens=1 delims==" %%c in ("%%b") do (
- if "%%c" equ "SERVER_USER" (
- echo %%c=456456456
- ) else if "%%c" equ "SERVER_PASSWORD" (
- echo %%c=456456456
- ) else echo=%%b
- if defined SERVER_USER if defined SERVER_PASSWORD (
- set m=
- )
- )) || echo=%%b
- ) else (
- if "%%b" equ "[SERVER_DATA_2]" (
- set m=1
- )
- echo=%%b
- )
- ))>"2.ini"
- move /y "2.ini" "1.ini"
- pause
复制代码
思维混乱写错了,修改一下
- @echo off
- (for /f "tokens=1* delims=:" %%a in ('findstr /n .* "1.ini"') do (
- if defined m (
- (for /f "tokens=1 delims==" %%c in ("%%b") do (
- if "%%c" equ "SERVER_USER" (
- echo %%c=456456456
- ) else if "%%c" equ "SERVER_PASSWORD" (
- echo %%c=456456456
- set m=
- ) else echo=%%b
- )) || echo=%%b
- ) else (
- if "%%b" equ "[SERVER_DATA_2]" (
- set m=1
- )
- echo=%%b
- )
- ))>"2.ini"
- move /y "2.ini" "1.ini"
- pause
复制代码
作者: wh7288 时间: 2023-7-31 12:34
本帖最后由 wh7288 于 2023-7-31 13:04 编辑
回复 12# Batcher
管理员大佬,您好.
本人刚接触多终端管理工作,也是在论坛上找到了很多提高工作效率的解决方案,在此略表谢意,感谢您和团队为新学习者做出的无私奉献.
1.如果是有多处相同的用户名\密码,我一般会增加一个变量,进行控制.
比如说 set "n=0" 如果有相同的server_user server_password, n+1
再对n进行判断,符合条件再输出赋值.
2.我没有理解您的意思,用户名密码不写在代码里,还能写在哪里?- if "%%a" equ "SERVER_USER" (
- echo,%%a=bbs.bathome.net
- set "ChangeU=true"
- ) else if "%%a" equ "SERVER_PASSWORD" (
- echo,%%a=www.bathome.net
- set "ChangeP=true"
- ) else (
- echo,!ThisRow!
- )
复制代码
按照我的理解,www.bathome.net就应该是用户名密码,不也是写在代码里?
请管理员大佬指点,谢谢.
作者: Batcher 时间: 2023-7-31 14:48
回复 14# wh7288
if "!str!" equ "SERVER_USER=456" (
不应该像这样使用【老用户名】作为判断条件
作者: aloha20200628 时间: 2023-7-31 15:55
针对一楼的简单样本,老老实实用纯P代码解了。
假设源文件是ANSI/简中编码- @echo off
- cd /d "D:\Program Files (x86)"
- set "newUser=abc" &set "newPw=999"
- setlocal enabledelayedexpansion
- (for /f "delims=" %%s in (src.ini) do if not defined got (
- (echo,%%s)
- if /i "%%s"=="[SERVER_DATA_2]" (set "got=1")
- ) else (
- if !got! equ 1 (set "newV=%newUser%") else (set "newV=%newPw%")
- for /f "tokens=1 delims==" %%1 in ("%%s") do (echo,%%1=!newV!)
- if !got! equ 2 (set "got=") else (set/a got+=1)
- )
- )>new.ini
- :: move /y new.ini src.ini REM 若保留源文件即注释此行
- endlocal &exit/b
复制代码
作者: Batcher 时间: 2023-7-31 16:06
回复 14# wh7288
这个场景下n+1写起来会比较麻烦(不是说完全不行),因为待修改的[SERVER_DATA_2]不一定出现在第几节。
作者: Batcher 时间: 2023-7-31 16:07
回复 6# 670422423
3楼第2段代码可以保留空行
作者: 670422423 时间: 2023-7-31 16:21
回复 7# Batcher
感谢管理员大佬。
作者: 670422423 时间: 2023-7-31 16:33
本帖最后由 670422423 于 2023-7-31 16:38 编辑
回复 18# Batcher
这个bat只能在原目录使用吧,要想在其他目录使用,比如文件在D:\Program Files (x86)\program\123.ini
然后把set "FileOld=123.ini"改为"FileOld=D:\Program Files (x86)\123.ini" 会报错 提示“系统找不到文件 \Program Files (x86)\123.ini"。”
作者: Batcher 时间: 2023-7-31 21:14
回复 20# 670422423
正常来说,没有这样的问题。
请再次仔细检查你的真实路径和写在代码里面的路径是否一样。
比如文件在D:\Program Files (x86)\program\123.ini
然后把set "FileOld=123.ini"改为"FileOld=D:\Program Files (x86)\123.ini" 会报错 提示“系统找不到文件 \Program Files (x86)\123.ini"。”
你给的这个例子明显不一致。
作者: 670422423 时间: 2023-8-2 11:16
回复 21# Batcher
感谢大佬指点迷津,问题已解决。以下是修改过的代码。- @echo off
- rem cd /d "%~dp0"
- setlocal EnableDelayedExpansion
-
- rem set "INPUT_FILE=file.txt"
- set "INPUT_FILE=D:\Program Files (x86)\input.ini"
- set "OUTPUT_FILE=D:\Program Files (x86)\output.ini"
- set "DATE_TIME=%date:~0,4%%date:~5,2%%date:~8,2%%time:~0,2%%time:~3,2%%time:~6,2%"
- set "BAK_FILE=D:\Program Files (x86)\common_bak%DATE_TIME%.ini"
- copy "%INPUT_FILE%" "%BAK_FILE%"
-
- rem 删除上次的输出文件
- if exist "%OUTPUT_FILE%" del "%OUTPUT_FILE%"
-
- for /f "usebackq tokens=1,2 delims=:" %%o in (`findstr /n .* "%INPUT_FILE%"`) do (
- rem echo %%p
- if "%%p" equ "" (
- rem 输出空行
- echo. >>"%OUTPUT_FILE%"
- ) else (
- for /f "tokens=1* delims==" %%c in ("%%p") do (
- if /i "%%c"=="[SERVER_DATA_3]" (
- set "Mod_flag=true"
- rem echo ----------------!Mod_flag!------------
- )
- rem 包含字符串“#""[”则仅输出%%c,否则进行修改
- echo %%c| findstr "# [" >nul && (
- set line=%%c
- ) || (
- rem 修改键值对
- if /i "!Mod_flag!" equ "true" (
- if /i "%%c" == "SERVER_USER" (
- rem echo %%d
- set line=%%c=cccccc
- set "ChangeU=true"
- ) else if /i "%%c" == "SERVER_PASSWORD" (
- rem echo %%d
- set line=%%c=cccccc
- set "ChangeP=true"
- ) else (
- set line=%%c=%%d
- )
- rem 全部修改完毕后,重置Mod_flag标识
- if /i "!ChangeU!" equ "true" (
- if /i "!ChangeP!" equ "true" (
- set "Mod_flag=false"
- )
- )
- ) else (
- set line=%%c=%%d
- )
- )
- REM 在此处修改line变量的值
- echo !line!>>"%OUTPUT_FILE%"
- )
- )
- )
-
- move /y "%OUTPUT_FILE%" "%INPUT_FILE%"
- endlocal
- echo "文件处理完成"
- pause
复制代码
欢迎光临 批处理之家 (http://www.bathome.net/) |
Powered by Discuz! 7.2 |