簡體   English   中英

configparser從zip加載配置文件

[英]configparser loading config files from zip

我正在創建一個程序,該程序從壓縮文件加載並運行python腳本。 除了這些python腳本外,我還有一個配置文件,我以前使用configparser從該程序的未壓縮版本中加載信息。

是否可以直接使用configparser直接讀取zip文件中的配置文件? 還是我必須將其解壓縮到一個臨時文件夾中並從那里加載它?

我嘗試直接給出路徑:

>>> sysconf = configparser.ConfigParser()
>>> sysconf.read_file("compressed.zip/config_data.conf")

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.4/configparser.py", line 691, in read_file
    self._read(f, source)
  File "/usr/local/lib/python3.4/configparser.py", line 1058, in _read
    raise MissingSectionHeaderError(fpname, lineno, line)
configparser.MissingSectionHeaderError: File contains no section headers.
file: '<???>', line: 1

沒用 沒有驚喜。

然后我嘗試使用zipfile

 >>> zf = zipfile.ZipFile("compressed.zip")
 >>> data = zf.read("config_data.conf")
 >>> sysconf = configparser.ConfigParser()
 >>> sysconf.read_file(data)

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.4/configparser.py", line 691, in read_file
    self._read(f, source)
  File "/usr/local/lib/python3.4/configparser.py", line 1009, in _read
    if line.strip().startswith(prefix):
AttributeError: 'int' object has no attribute 'strip'

並發現它也不起作用。

因此,我不得不創建一個臨時文件夾,將其解壓縮,然后在其中讀取conf文件。 我真的想避免這種情況,因為conf文件是唯一的限制因素。 此時,我可以(也可以)從zip文件加載python模塊。

如果有一種方法可以將其直接傳遞給configparser,則可以獲取文件的原始文本,但是我空手搜索我找到的文檔。

更新:我嘗試將stringIO用作文件對象,但似乎有些正常。 configparser不會拒絕它,但是也不喜歡它。

>>> zf = zipfile.ZipFile("compressed.zip")
>>> data = zf.read(config_data.conf)
>>> confdata = io.StringIO(str(data))
>>> sysconf = configparser.ConfigParser()
>>> sysconf.readfp(confdata)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.4/configparser.py", line 736, in readfp
    self.read_file(fp, source=filename)
  File "/usr/local/lib/python3.4/configparser.py", line 691, in read_file
    self._read(f, source)
  File "/usr/local/lib/python3.4/configparser.py", line 1058, in _read
    raise MissingSectionHeaderError(fpname, lineno, line)
configparser.MissingSectionHeaderError: File contains no section headers.
file: '<???>', line: 1
(continues to spit out the entire contents of the file)

如果我改用read_file,它不會出錯,但也不會加載任何東西。

>>> zf = zipfile.ZipFile("compressed.zip")
>>> data = zf.read(config_data.conf)
>>> confdata = io.StringIO(str(data))
>>> sysconf = configparser.ConfigParser()
>>> sysconf.read_file(confdata)
>>> sysconf.items("General") #(this is the main section in the file)
Traceback (most recent call last):
  File "/usr/local/lib/python3.4/configparser.py", line 824, in items
    d.update(self._sections[section])
KeyError: 'General'

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python3.4/configparser.py", line 827, in items
    raise NoSectionError(section)
configparser.NoSectionError: No section: 'General'

如果有一種方法可以直接將其傳遞給configparser,則可以獲取文件的原始文本

嘗試configparser.ConfigParser.read_string

結合適當的ZIP文件后,此代碼對我有用:

import zipfile
import configparser

zf = zipfile.ZipFile("compressed.zip")
zf_config = zf.open("config_data.conf", "rU")
zf_config_data = zf_config.read().decode('ascii')

config = configparser.ConfigParser()
config.read_string(zf_config_data)
assert config['today']['lunch']=='cheeseburger'

經過反思,以下內容可能更合適:

import zipfile
import configparser
import io

zf = zipfile.ZipFile("compressed.zip")
zf_config = zf.open("config_data.conf", "rU")
zf_config = io.TextIOWrapper(zf_config)

config = configparser.ConfigParser()
config.read_file(zf_config)
assert config['today']['lunch']=='cheeseburger'

ZipFile不僅支持read ,還支持open ,它返回一個類似文件的對象。 因此,您可以執行以下操作:

zf = zipfile.ZipFile("compressed.zip")
config_file = zf.open("config_data.conf")
sysconfig = configparser.ConfigParser()
sysconfig.readfp(config_file)

正如評論中所寫,@ matthewatabet答案不適用於Python 3.4(和較新版本)。 這是因為ZipFile.open現在返回的是“字節狀”對象,而不是“文件狀”對象。 您可以使用:

codecs.getreader("utf-8")(config_file)

使用UTF-8編碼將config_file類似字節的對象轉換為類似文件的對象。 現在的代碼是:

import zipfile, configparser, codecs

with zipfile.ZipFile("compressed.zip") as zf:
    config_file = zf.open("config_data.conf")
    sysconfig = configparser.ConfigParser()
    sysconfig.read_file(codecs.getreader("utf-8")(config_file))

這似乎比創建string更令人滿意,但我不知道它是否更有效...

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM