adafruit / circuitpython

CircuitPython - a Python implementation for teaching coding with microcontrollers
https://circuitpython.org
Other
4.12k stars 1.22k forks source link

Can't perform relative import in the root folder #9774

Closed leogout closed 3 weeks ago

leogout commented 3 weeks ago

CircuitPython version

Adafruit CircuitPython 9.2.0 on 2024-10-30; Raspberry Pi Pico with rp2040

Code/REPL

from .test import test

print('main.py')

Behavior

Auto-chargement activé. Copiez ou sauvegardez les fichiers via USB pour les lancer ou démarrez le REPL pour le désactiver.
code.py sortie :
Traceback (appels les plus récents en dernier) :
  Fichier "code.py", ligne 1, dans <module>
ImportError: ne peut importer relativement
Exécution du code terminée.
Appuyez sur n'importe quelle touche pour utiliser le REPL. Utilisez CTRL-D pour relancer.

Which translates to :

Auto-reload enabled. Copy or save files via USB to run them or start the REPL to disable it.
code.py output:
Traceback (most recent calls last):
File "code.py", line 1, in <module>
ImportError: cannot import relatively
Code execution finished.

Press any key to use the REPL. Use CTRL-D to reload.

Description

I have the following files structure : image In the test folder : image And here is the source code for the main.py and the test.py :

from .test import test

print('main.py')
print('test.py')

Additional information

The hardware connection is done through USB on Windows 10, the output logs are on COM4, reading them with putty.

Further investigation reveals that relative imports from non root folders works : image image If I remove the relative import in the code.py and use one in the test/test.py, it works as expected :

# code.py
from test import test

print('code.py')
# test/code.py
from .test_deeper import test

print('test.py')
# test/test_deeper/test.py
print('test_deeper.py')

Output :

Auto-chargement activé. Copiez ou sauvegardez les fichiers via USB pour les lancer ou démarrez le REPL pour le désactiver.
code.py sortie :
test_deeper.py
test.py
code.py

Exécution du code terminée.

Appuyez sur n'importe quelle touche pour utiliser le REPL. Utilisez CTRL-D pour relancer.
jepler commented 3 weeks ago

The relative import syntax is for modules that are within a package, but the main Python code does not reside "in a package". You get something similar when you try to perform the same action on standard desktop Python (3.11 on my system), though the message is different:

$ echo 'from .test import test' > issue9774.py
$ python issue9774.py 
Traceback (most recent call last):
  File "/home/jepler/issue9774.py", line 1, in <module>
    from .test import test
ImportError: attempted relative import with no known parent package
jepler commented 3 weeks ago

You may mean to write from test import test instead

leogout commented 3 weeks ago

I should mention that I need relative imports in the root folder for the following reason (hope I'll avoid the XY problem) :

Oh okay thanks @jepler, I did not know that. I'll try to find another solution !

jepler commented 3 weeks ago

At least the following 4 names are always supported for the primary code file:

            "code.txt", "code.py", "main.py", "main.txt"

so maybe one of the .txt files would help with what you're trying to do.

leogout commented 3 weeks ago

Well thanks @jepler, you just made my day

mMerlin commented 3 weeks ago

At least the following 4 names are always supported for the primary code file:

            "code.txt", "code.py", "main.py", "main.txt"

so maybe one of the .txt files would help with what you're trying to do.

I use main.py exactly for that reason. It allows me to run unittests both with CPython on the desktop computer, and in Circuitpython. No complaints about shadowing.