Pertanyaan Data Akses Python dalam Subdirektori Paket


Saya menulis paket python dengan modul yang perlu membuka file data dalam file ./data/ subdirektori. Saat ini saya memiliki jalur ke file yang dikodekan ke dalam kelas dan fungsi saya. Saya ingin menulis kode yang lebih kuat yang dapat mengakses subdirektori di mana pun itu diinstal pada sistem pengguna.

Saya sudah mencoba berbagai metode, tetapi sejauh ini saya tidak beruntung. Tampaknya sebagian besar perintah "direktori saat ini" mengembalikan direktori interpreter python sistem, dan bukan direktori modul.

Sepertinya ini seharusnya menjadi masalah umum yang sepele. Namun saya tidak bisa mengetahuinya. Sebagian masalahnya adalah file data saya tidak .py file, jadi saya tidak bisa menggunakan fungsi impor dan sejenisnya.

Ada saran?

Saat ini direktori paket saya terlihat seperti:

/
__init__.py
module1.py
module2.py
data/   
   data.txt

Saya mencoba mengakses data.txt dari module*.py

Terima kasih!


76
2018-04-22 22:17


asal


Jawaban:


Anda dapat menggunakan underscore-underscore-file-underscore-underscore (__file__) untuk mendapatkan jalur ke paket, seperti ini:

import os
this_dir, this_filename = os.path.split(__file__)
DATA_PATH = os.path.join(this_dir, "data", "data.txt")
print open(DATA_PATH).read()

23
2018-04-22 22:37



Cara standar untuk melakukan ini adalah dengan paket setuptools dan pkg_resources.

Anda dapat menata paket sesuai dengan hierarki berikut, dan mengonfigurasi file pengaturan paket untuk mengarahkannya ke sumber data Anda, sesuai tautan ini:

http://docs.python.org/distutils/setupscript.html#installing-package-data

Anda kemudian dapat menemukan kembali dan menggunakan file tersebut menggunakan pkg_resources, sesuai tautan ini:

http://peak.telecommunity.com/DevCenter/PkgResources#basic-resource-access

import pkg_resources

DATA_PATH = pkg_resources.resource_filename('<package name>', 'data/')
DB_FILE = pkg_resources.resource_filename('<package name>', 'data/sqlite.db')

109
2018-04-08 23:42



Untuk memberikan solusi yang berfungsi hari ini. Gunakan API ini untuk tidak menemukan kembali semua roda tersebut.

Nama file sistem file yang sebenarnya diperlukan. Telur zip akan diekstrak ke direktori cache:

from pkg_resources import resource_filename, Requirement

path_to_vik_logo = resource_filename(Requirement.parse("enb.portals"), "enb/portals/reports/VIK_logo.png")

Kembalikan objek seperti file yang dapat dibaca untuk sumber daya yang ditentukan; mungkin file yang sebenarnya, StringIO, atau objek serupa. Aliran ini dalam "mode biner", dalam arti bahwa apa pun byte dalam sumber daya akan dibaca apa adanya.

from pkg_resources import resource_stream, Requirement

vik_logo_as_stream = resource_stream(Requirement.parse("enb.portals"), "enb/portals/reports/VIK_logo.png")

Paket Penemuan dan Akses Sumber Daya menggunakan pkg_resources


12
2017-10-09 12:33



Saya pikir saya memburu jawaban.

Saya membuat modul data_path.py, yang saya impor ke modul saya yang lain yang berisi:

data_path = os.path.join(os.path.dirname(__file__),'data')

Dan kemudian saya membuka semua file saya

open(os.path.join(data_path,'filename'), <param>)

6
2018-04-22 22:35



Anda perlu nama untuk seluruh modul Anda, Anda diberi pohon direktori tidak mencantumkan detail itu, bagi saya ini bekerja:

import pkg_resources
print(    
    pkg_resources.resource_filename(__name__, 'data/data.txt')
)

Noteless setuptools tidak muncul untuk menyelesaikan file berdasarkan nama yang cocok dengan file data yang dikemas, jadi Anda harus memasukkan data/ awalan cukup banyak tidak peduli apa. Kamu dapat memakai os.path.join('data', 'data.txt) jika Anda memerlukan pemisah direktori alternatif, Secara umum saya tidak menemukan masalah kompatibilitas dengan pemisah direktori unix style keras-kode sekalipun.


5
2017-12-10 09:59