I wrote a Python script which is executed via Jython 2.7. I need SQLite, so I decided to use sqlite3 for Jython (link) which is under /usr/local/lib/jython/Lib.
ghidra_batch.py
import sys
sys.path.append("/usr/local/lib/jython/Lib")
sys.path.append("/path/to/my/project/directory")
import sqlite3
I created another file where I define some functions for my database:
db.py
import platform
import sys
if platform.python_implementation == 'Jython':
sys.path.append("/usr/local/lib/jython/Lib")
sys.path.append("/path/to/my/project/directory")
import sqlite3
def open_db():
[some code]
def create_schema():
[some code]
Note: I check Python implementation because this script is run also via CPython. I append the path only when run via Jython to make it find its sqlite3 module, in case of CPython standard sqlite3 module is used.
Now my problem happens when I import open_db() in ghidra_batch.py:
from db import open_db
The result is the following:
ImportError: cannot import name open_db
Thanks for your help.
As a general rule: when working with Python, when something isn't not what you're expecting, simply print it.
Your from db import open_db line which was triggering that exception "told" me that:
The db module (package) was found
It's not the one that you're expecting to be (your db.py)
That's why I suggested in my comment to print information about it (obviously, before the error is hit):
import db
print(db)
print(dir(db))
The output confirmed it. So, there is another db module which is imported before yours. I tried replicating your environment (installed Jython, but I wasn't able to install jython-sqlite3).
After a bit of research, I think it's [BitBucket]: Taro L. Saito/sqlite-jdbc/Source - sqlite-jdbc/src/main/java/org/sqlite/DB.java (sqlite-jdbc is a jython-sqlite3 dependency).
The reasonable way is to modify your module name to something else (e.g.: sqlite_db_wrapper.py), and also update the import statement(s).
As a(n other) general rule, don't give your modules (common) names that might conflict with modules from Python's library.
Related
How can I convert an asciidoc to html using the asciidoc3 python package from within my python script? I'm not able to find a working example. The official docs are oriented mainly towards those who will use asciidoc3 as a command line tool, not for those who wish to do conversions in their python apps.
I'm finding that sometimes packages are refactored with significant improvements and old examples on the interwebs are not updated. Python examples frequently omit import statements for brevity, but for newer developers like me, the correct entry point is not obvious.
In my venv, I ran
pip install asciidoc3
Then I tried...
import io
from asciidoc3.asciidoc3api import AsciiDoc3API
infile = io.StringIO('Hello world')
outfile = io.StringIO()
asciidoc3_ = AsciiDoc3API()
asciidoc3_.options('--no-header-footer')
asciidoc3_.execute(infile, outfile, backend='html4')
print(outfile.getvalue())
and
import io
from asciidoc3 import asciidoc3api
asciidoc3_ = asciidoc3api.AsciiDoc3API()
infile = io.StringIO('Hello world')
asciidoc3_.execute(infile)
Pycharm doesn't have a problem with either import attempt when it does it's syntax check and everything looks right based on what I'm seeing in my venv's site-packages... "./venv/lib/python3.10/site-packages/asciidoc3/asciidoc3api.py" is there as expected. But both of my attempts raise "AttributeError: module 'asciidoc3' has no attribute 'execute'"
That's true. asciidoc3 doesn't have any such attribute. It's a method of class AsciiDoc3API defined in asciidoc3api.py. I assume the problem is my import statement?
I figured it out. It wasn't the import statement. The error message was sending me down the wrong rabbit hole but I found this in the module's doc folder...
[NOTE]
.PyPI, venv (Windows or GNU/Linux and other POSIX OS)
Unfortunately, sometimes (not always - depends on your directory-layout, operating system etc.) AsciiDoc3 cannot find the 'asciidoc3' module when you installed via venv and/or PyPI. +
The solution:
from asciidoc3api import AsciiDoc3API
asciidoc3 = AsciiDoc3API('/full/path/to/asciidoc3.py')
I have a module that conflicts with a built-in module. For example, a myapp.email module defined in myapp/email.py.
I can reference myapp.email anywhere in my code without issue. However, I need to reference the built-in email module from my email module.
# myapp/email.py
from email import message_from_string
It only finds itself, and therefore raises an ImportError, since myapp.email doesn't have a message_from_string method. import email causes the same issue when I try email.message_from_string.
Is there any native support to do this in Python, or am I stuck with renaming my "email" module to something more specific?
You will want to read about Absolute and Relative Imports which addresses this very problem. Use:
from __future__ import absolute_import
Using that, any unadorned package name will always refer to the top level package. You will then need to use relative imports (from .email import ...) to access your own package.
NOTE: The above from ... line needs to be put into any 2.x Python .py files above the import ... lines you're using. In Python 3.x this is the default behavior and so is no longer needed.
so I'm new to Python and Flask and I'm currently playing around with some CRUD-statements within Flask/Python
I want to know if I fully understand what's going on but I'm a little bit unsecure regarding the following topic: Modules, Packages import
I want to connect to my SQLite database with Flask. Doing so, I have to do some imports:
import os
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
First thing after the imports are done is to set a basedirectory (=basedir):
basedir = os.path.abspath(os.path.dirname(__file__))
And regarding those steps I have some questions:
Question:
import os
from flask import Flask
Does the first import ("import os") mean that I'm only using a Module called "os"? It's a standalone .py - "file" including a class, some attributes and methods, right?
Does the second import ("from flask import Flask") mean that I'm using the package "flask" and import the module "Flask"? If, e.g., there would be another import like "render_template", does that mean I'm using this module or is it a method from the module "Flask"?
Second question:
basedir = os.path.abspath(os.path.dirname(__file__))
I'd like to understand this code. First of all, I'm declaring a variable called basedir. Then I am going to set the value of that variable to the absolute path for the current .py-script. Now to the single steps:
os => means that I'm using the already imported module "os", right?
path => means that I'm using an attribute from that module?
abspath => means that I'm using a method within the "os" module called "abspath(value)"?
The next thing would be clear if I get an answer to the other things: "
(os.path.dirname(__filename__))
__filename__ => that's a built-in Python attribute, right?
Does the first import ("import os") mean that I'm only using a Module called "os"?
As the statement implies, you're importing the OS module, so you can use the functions in the os module in your python script.
So, now you can make os.function() statements in your script. The OS module is installed with Python by default. Here is info on the os module.
Does the second import ("from flask import Flask") mean that I'm using the package "flask" and import the module "Flask"? If, e.g., there would be another import like "render_template", does that mean I'm using this module or is it a method from the module "Flask"?
This can be confusing since the function name and the import statement have the same name. You're only importing the function flask from the module Flask, not all the functions present in the Flask module.
This can be done for multiple reasons. On is to simplify calling the function. Another could be to save system resources, since you're only
os => means that I'm using the already imported module "os", right? path => means that I'm using an attribute from that module? abspath => means that I'm using a method within the "os" module called "abspath(value)"?
Exactly, read the docs for an explanation by the developers of the module.
Filename
Here is an explanation of the filename usage in Python.
Im gonna answer the first question. Basically when you do just an import, python imports the entire file with all of its modules and functions. Like when you import math you can use math.ceil and other functions. However when you say from math import add you only get a specific module which is ceil like ceil(2.7).
For further details read up here
I am writing a web app using python3, venv and c9.io PAAS. I have the following structure of my code:
batch_runner.py
logic/
__init__.py
parsers/
__init__.py
time_parser.py
abstract_parser.py
here batch_runner imports abstract_parser, which, in it turn, import from time_parser. everything was installed and runs with venv activated.
To be specific, batch_runner.py contains:
from logic.parsers import abstract
from sys import argv
url = argv[1]
a = abstract(url)
logic/__init__.py is empty. logic/parsers/__init__.py contains:
from abstract_parser import abstract
from time_parser import _timeInfo
If I go to logic and run python abstract_parser.py directly, everything works as expected. However, if I go one level up, and run python batch_runner.py, it is able to import abstract_parser, but it can't find time_parser which is called from abstract_parser, throwing ImportError: No module named 'abstract'
Change this:
from abstract_parser import abstract
To
from logic.parsers.abstract_parser import abstract
Do read about importing from the python documentation on modules.
In this case, one possible solution is to use relative imports inside your package:
That is, in logic/parsers/__init__.py, use:
from .abstract_parser import abstract
from .time_parser import _timeInfo
and in abstract_parser.py:
from .time_parser import _timeInfo
This should let parsers/__init__.py find the abstract_parser module and the time_parser module.
The python import system has a surprising number of traps that you can fall into. This blog post by Nick Coghlan describes many of them, and I personally consider it a must-read if you're planning to develop a package.
So my first python program, I downloaded the macholib package from PYPI, then unzipped it and ran installed the setup.py using python install, now I'm trying to run a program where I first import the macholib, then when I try to access methods like Macho, it gives me an error saying macholib module has no attributes called Macho.
My understanding is macholib is a package and not a module or something, hence I cant use the contents of the package.
Please answer, I've wasted too much time on such a simple newbie issue.
running a mac with the latest version of python.
Code:
import sys
import macholib
MachO(DivXInstaller.dmg)
I tried macholib.MachO(DivXInstaller.dmg) and macholib.MachO.MachO(DivXInstaller.dmg)
Error for python test.py
Traceback (most recent call last):
File "test.py", line 3, in <module>
MachO(DivXInstaller.dmg)
NameError: name 'MachO' is not defined
You have this line in your code:
MachO(DivXInstaller.dmg)
However, the name MachO is not defined anywhere. So Python tells you this with the error
NameError: name 'MachO' is not defined
If you want to use the MachO module under the name MachO, you have to import it:
from macholib import MachO
This you have not done, which is the cause of your error. All you did was
import macholib
which gives you the name "macholib" that you can use. However, macholib contains mostly submodules which you can not access like that, so that is not particularly useful. If you don't want to pollute the namespace, you can import MachO as
import machlibo.MachO
Which gives you access to the MachO module as macholib.MachO
You haven't defined DivXInstaller.dmg either, so that's going to be your next error. I recommend that you go through a Python tutorial before you start programming in it.
An import statement defines a namespace. Hence, in order to use something defined in the module or package, you need to qualify it. In this case, the module itself is macholib.MachO but you need to dig deeper, to the actual class MachO which, slightly confusingly, has the same name, so you need to import macholib.MachO and use macholib.MachO.MachO (note that when I try to do this I get an error "DistributionNotFound: altgraph", however).
Note further that it takes a filename as an argument, which is a string. Moreover, you are actually creating an instance of a class, so you probably mean
mlib = macholib.MachO.MachO("DivXInstaller.dmg")
where now mlib is actually the object you need to manipulate with further calls...
Alternately you can do from macholib import MachO or even from macholib.MachO import MachO so you could use MachO.MachO(...) or MachO(...) directly.
This is so simple if you understand Python Packages vs. Modules and import vs. from import:
A Python module is simply a Python source file.
A Python package is simply a directory of Python module(s).
1- import:
import package1.package2.module1
To access module1 classes, functions or variables you should use the whole namespace: package1.package2.modlue1.class1
You cannot import a class or function this way: (wrong)
import package1.package2.class1
2- from ... import
Instead use "from" to import a single class, function or variable of a module:
from package1.package2.module1 import class1
no need to address the whole namespace: class1.method1() works now
Note that you cannot import a method of a class this way
Example:
datetime is a class of module datetime that has a method called utcnow(), to access utcnow() one could:
import datetime
datetime.datetime.utcnow()
Or
from datetime import datetime
datetime.utcnow()