diddi- / flask-seeder

Flask extension for seeding database
32 stars 11 forks source link

Can't list seeders #12

Closed GuteFCO closed 3 years ago

GuteFCO commented 3 years ago

When I run flask seed list it fails when I have some project import. It can be fixed adding @with_appcontext to seed_list on cli.py

diddi- commented 3 years ago

I'm not sure I understand what issue you are facing. Could you add some minimal code to reproduce this, and what kind of errors you are getting?

GuteFCO commented 3 years ago

My project have the following structure

- src
  - migrations
  - project
    - __init__.py
    - localization
      - __init__.py
      - models.py  
  - seeds
    - countries.py
  - app.py

In the seeds folder I have the file countries.py with this code

from flask_seeder import Seeder
from project.localization.models import Country

class CountriesSeeder(Seeder):
    def run(self):
        countries = [Country()]

    for country in countries:
        self.db.session.add(country)

When I run flask seed run all works correctly, but when I run flask seed list I get the following error

Traceback (most recent call last):
  File "/usr/local/bin/flask", line 8, in <module>
    sys.exit(main())
  File "/usr/local/lib/python3.9/site-packages/flask/cli.py", line 967, in main
    cli.main(args=sys.argv[1:], prog_name="python -m flask" if as_module else None)
  File "/usr/local/lib/python3.9/site-packages/flask/cli.py", line 586, in main
    return super(FlaskGroup, self).main(*args, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/click/core.py", line 782, in main
    rv = self.invoke(ctx)
  File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1259, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1259, in invoke
    return _process_result(sub_ctx.command.invoke(sub_ctx))
  File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1066, in invoke
    return ctx.invoke(self.callback, **ctx.params)
  File "/usr/local/lib/python3.9/site-packages/click/core.py", line 610, in invoke
    return callback(*args, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/flask_seeder/cli.py", line 192, in seed_list
    for seeder in get_seeders(root=root):
  File "/usr/local/lib/python3.9/site-packages/flask_seeder/cli.py", line 122, in get_seeders
    seeders.extend(get_seeders_from_script(script))
  File "/usr/local/lib/python3.9/site-packages/flask_seeder/cli.py", line 97, in get_seeders_from_script
    spec.loader.exec_module(module)
  File "<frozen importlib._bootstrap_external>", line 790, in exec_module
  File "<frozen importlib._bootstrap>", line 228, in _call_with_frames_removed
  File "seeds/regions.py", line 2, in <module>
    from project.localization.models import Region
ModuleNotFoundError: No module named 'project'

This error is fixed when I add @with_appcontext to the seed_list function on cli.py just like the function seed_run

diddi- commented 3 years ago

The reason you get ModuleNotFoundError when running flask seed list is because the project folder is not in the Python path sys.path.

@with_appcontext will do a whole lot more than just help with imports. The entire Flask application will be created which is a bit much given we only want to list the seeders.

You have a few options depending on your setup and preference:

  1. Install your package as editable pip install --editable . (requires a setup.py)
  2. Set/export the PYTHONPATH variable to the current directory: PYTHONPATH=. flask seed list
  3. Run it from python directly python -m flask seed list

Any of the above will work but if you intend to package and distribute your project a common approach is to install it as an editable package.