5

I want to edit the value of INI file. I use this script but It gives me error.

Get-IniContent : The term 'Get-IniContent' is not recognized as the name of a 
cmdlet, function, script file, or operable program.

The contents of my INI file at c:\Users\file.ini:

[XXX]
AB=23
BC=34

The contents of the script for reading and updating it:

# Read the content of an *.ini file into a (nested) hashtable.
$ini = Get-IniContent "C:\Users\file.ini"

# Update the 'AB' entry in section [XXX] in-memory.
$ini["XXX"]["AB"] = "12"  

# Write the updated content back to the *.ini file.
$ini | Out-IniFile -FilePath "C:\Users\file.ini -Force"
2
  • 4
    That's because Get-IniContent is not a standard cmdlet included in a vanilla PowerShell installation. (Neither is Out-IniFile.) There are various scripts online offering such cmdlets, but you'll have to import them in your session first to get them. Try Import-Module PsIni -- you may need to install it first, though. Commented Mar 25, 2019 at 13:23
  • Under Windows 11, you will need to set the execution policy on the machine before you can import PsIni: "Set-ExecutionPolicy -ExecutionPolicy RemoteSigned" Commented Nov 9 at 1:34

2 Answers 2

7

JeroenMostert has provided the crucial pointer in a comment:

PowerShell, as of v7.2.x, has no built-in cmdlets for processing INI files (*.ini), though introducing such cmdlets is being discussed in GitHub issue #9035.

Get-IniContent and Out-IniFile are advanced functions (cmdlet-like functions) that come with the third-party PSIni module, available from the PowerShell Gallery.

In PowerShell v5 or higher, which comes with the PowerShellGet module[1], installation is as easy as:

Install-Module -Scope CurrentUser PsIni

If you omit -Scope CurrentUser, you'll install the module for all users, but doing so requires running with administrative privileges.

With $PSModuleAutoLoadingPreference at its default (unset), this module is then loaded automatically, on demand into a session that tries to call one of the module's commands, such as Get-IniContent.

Here's a complete, self-contained example that exercises the core functionality of the PsIni module:

  • installs the module on demand
  • creates a sample *.ini file from scratch with Out-IniFile, from a nested ordered hashtable.
  • reads the file from disk with Get-IniContent into a (new) nested ordered hashtable
  • modifies and removes entries
  • writes the modified hashtable back to the file with Out-IniFile

Note: The assumptions are that Install-Module is available, i.e., that the PowerShellGet module is installed, and that the running machine is online and permitted to download packages from https://www.powershellgallery.com/.

# Import the PsIni module.
# If necessary, install it first, for the current user.
$ErrorActionPreference = 'Stop' # Abort, if something unexpectedly goes wrong.
try {
  Import-Module PsIni
} catch {
  Install-Module -Scope CurrentUser PsIni
  Import-Module PsIni
}

# Create an ordered hashtable that is the in-memory representation of the
# sample *.ini file from the question, with a second section added.
$iniFileContent = [ordered] @{
  # 'XXX' is the section name.
  # The nested hashtable contains that section's entries.
  XXX = [ordered] @{  
    # IMPORTANT: 
    #  * The PsIni module only supports STRING values.
    #  * While you can assign values of different types in-memory, they are
    #    CONVERTED TO STRINGS with .ToString() and READ AS STRINGS later
    #    by Get-IniContent.
    #  * In v3+, PSIni now supports values in *.ini files that have 
    #    embedded quoting - e.g., `AB = "23"` as a raw line - which is
    #    (sensibly) *stripped* on reading the values.
    AB = '23'
    BC = '34'
  }
  # Create a 2nd section, named 'YYY', with entries 'yin' and 'yang'
  YYY = [ordered] @{
    yin = 'foo'
    yang = 'none'
  }
}

# Use Out-IniFile to create file 'file.ini' in the current dir.
# * Default encoding is UTF-8 (with BOM in Windows PowerShell, without BOM
#   in PowerShell Core)
# * Use -Encoding to override, but note that
#   Get-IniContent has no matching -Encoding parameter, so the encoding you use
#   must be detectable by PowerShell in the absence of explicit information.
# * CAVEAT: -Force is only needed if an existing file must be overwritten.
#           I'm using it here so you can run the sample code repeatedly without
#           failure, but in general you should only use it if you want to
#           blindly replace an existing file - such as after having modified
#           the in-memory representation of an *.ini file and wanting to
#           write the modifications back to disk - see below.
$iniFileContent | Out-IniFile -Force file.ini

# Read the file back into a (new) ordered hashtable 
$iniFileContent = Get-IniContent file.ini

# Modify the value of the [XXX] section's 'AB' entry.
$iniFileContent.XXX.AB = '12'

# Use the alternative *indexing syntax* (which is equivalent in most cases)
# to also modify the [YYY] section's 'yin' entry.
$iniFileContent['YYY']['yin'] = 'bar'

# Remove the 'yang' value from section [YYY]:
$iniFileContent.YYY.Remove('yang')

# Save the modified content back to the original file.
# Note that -Force is now *required* to signal the explicit intent to
# replace the existing file.
$iniFileContent | Out-IniFile -Force file.ini

# Double-check that modifying the values succeeded.
(Get-IniContent file.ini).XXX.AB # should output '12'
(Get-IniContent file.ini).YYY.yin # should output 'bar'

# Print the updated content of the INI file, which
# shows the updated values and the removal of 'yang' from [YYY].
"--- Contents of file.ini:"
Get-Content file.ini

Running the above should succeed and output the following, demonstrating that the *.ini file was successfully created, read back into memory, modified, and saved back to disk:

12
bar
--- Contents of file.ini:
[XXX]
AB=12
BC=34
[YYY]
yin=bar

[1] You can install PowerShellGet on demand for PowerShell versions 3 and 4 - see https://www.microsoft.com/en-us/download/details.aspx?id=51451

Sign up to request clarification or add additional context in comments.

Comments

0

Since I am new to powershell when I read this post I first thought I had to use the cmdlets to read and write Ini-Files. However, it is not necessary.

$ini= [System.IO.File]::ReadAllText("c:\temp\test.ini")
[System.IO.File]::WriteAllText("c:\temp\test2.ini", $ini)

This works as well...just wanted to share :)

1 Comment

Yes, you can read and write any text file this way (although you'd use Get-Content and Set-Content in PowerShell for that), but your answer has nothing to with the question at hand, which is about programmatic access to the object model that the .ini file format represents.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.