<p>I've written a Python package that includes a bsddb database of pre-computed values for one of the more time-consuming computations.  For simplicity, my setup script installs the database file in the same directory as the code which accesses the database (on Unix, something like /usr/lib/python2.5/site-packages/mypackage/).</p>

<p>How do I store the final location of the database file so my code can access it?  Right now, I'm using a hack based on the <code>__file__</code> variable in the module which accesses the database:</p>

<pre>
dbname = os.path.join(os.path.dirname(__file__), "database.dat")
</pre>

<p>It works, but it seems... hackish.  Is there a better way to do this?  I'd like to have the setup script just grab the final installation location from the distutils module and stuff it into a "dbconfig.py" file that gets installed alongside the code that accesses the database.</p>

[{'answer_id': 39295, 'author': 'dguaraglia', 'author_id': 2384, 'author_profile': 'https://Stackoverflow.com/users/2384', 'pm_score': 2, 'selected': False, 'text': "<p>That's probably the way to do it, without resorting to something more advanced like using setuptools to install the files where they belong.</p>\n\n<p>Notice there's a problem with that approach, because on OSes with real a security framework (UNIXes, etc.) the user running your script might not have the rights to access the DB in the system directory where it gets installed.</p>\n"}, {'answer_id': 39659, 'author': 'Aaron Maenpaa', 'author_id': 2603, 'author_profile': 'https://Stackoverflow.com/users/2603', 'pm_score': 5, 'selected': False, 'text': '<p>Try using pkg_resources, which is part of setuptools (and available on all of the pythons I have access to right now):</p>\n\n<pre><code>&gt;&gt;&gt; import pkg_resources\n&gt;&gt;&gt; pkg_resources.resource_filename(__name__, "foo.config")\n\'foo.config\'\n&gt;&gt;&gt; pkg_resources.resource_filename(\'tempfile\', "foo.config")\n\'/usr/lib/python2.4/foo.config\'\n</code></pre>\n\n<p>There\'s more discussion about using pkg_resources to get resources on the <a href="http://peak.telecommunity.com/DevCenter/PythonEggs#accessing-package-resources" rel="noreferrer">eggs</a> page and the <a href="http://peak.telecommunity.com/DevCenter/PkgResources" rel="noreferrer">pkg_resources</a> page.</p>\n\n<p>Also note, where possible it\'s probably advisable to use pkg_resources.resource_stream or pkg_resources.resource_string because if the package is part of an egg, resource_filename will copy the file to a temporary directory.</p>\n'}, {'answer_id': 9918496, 'author': 'merwok', 'author_id': 821378, 'author_profile': 'https://Stackoverflow.com/users/821378', 'pm_score': 4, 'selected': False, 'text': '<p>Use <code>pkgutil.get_data</code>. It’s the cousin of <code>pkg_resources.resource_stream</code>, but in the standard library, and should work with flat filesystem installs as well as zipped packages and other importers.</p>\n'}, {'answer_id': 56714420, 'author': 'ankostis', 'author_id': 548792, 'author_profile': 'https://Stackoverflow.com/users/548792', 'pm_score': 2, 'selected': False, 'text': '<p>Use the standard Python-3.7 library\'s <a href="https://docs.python.org/3.8/library/importlib.html?highlight=importlib#module-importlib.resources" rel="nofollow noreferrer"><code>importlib.resources</code> module</a>, \nwhich is <a href="https://importlib-resources.readthedocs.io/en/latest/using.html#example" rel="nofollow noreferrer">more efficient</a> than <a href="http://setuptools.readthedocs.io/en/latest/pkg_resources.html#basic-resource-access" rel="nofollow noreferrer"><code>setuptools:pkg_resources</code></a>\n(on previous Python versions, use the backported <a href="https://importlib-resources.readthedocs.io/en/latest/using.html" rel="nofollow noreferrer"><code>importlib_resources</code> library</a>).</p>\n\n<p><strong>Attention:</strong> For this to work, the folder where the data-file resides <em>must be a regular python-package</em>.  That means you must add an <code>__init__.py</code> file into it, if not already there.</p>\n\n<p>Then you can access it like this:</p>\n\n<pre class="lang-py prettyprint-override"><code>try:\n  import importlib.resources as importlib_resources\nexcept ImportError:\n  # In PY&lt;3.7 fall-back to backported `importlib_resources`.\n  import importlib_resources\n\n\n## Note that the actual package could have been used, \n#  not just its (string) name, with something like: \n#      from XXX import YYY as data_pkg\ndata_pkg = \'.\'\nfname = \'database.dat\'\n\ndb_bytes = importlib_resources.read_binary(data_pkg, fname)\n# or if a file-like stream is needed:\nwith importlib_resources.open_binary(data_pkg, fname) as db_file:\n    ...\n</code></pre>\n'}]
['https://Stackoverflow.com/questions/39104', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/4198/']