alefeans / pycommerce

Ecommerce example application built with modern Python πŸš€
MIT License
6 stars 1 forks source link

[question] How fast is it on Agile? #2

Open leonardomarcao opened 5 months ago

leonardomarcao commented 5 months ago

Hi Álefe, how are you?

Congratulations on the repository, this project is beautiful and applies good modern practices.

I have a question, in your opinion, how fast is the usage of this structure/architecture project developing a small/medium project size?

For example, imagine I want to add a new entity called Order, what is the flow, and how much time will be spent to develop this? Of course, this depends on more detailed context and I apologize for this, but consider this question generic.

alefeans commented 2 months ago

Hi @leonardomarcao, I apologize for the delay and hope you're doing well!

Thanks for the feedback and for expressing your interest in pycommerce, I appreciate it! Now, to your questions:

I have a question, in your opinion, how fast is the usage of this structure/architecture project developing a small/medium project size?

For example, imagine I want to add a new entity called Order, what is the flow, and how much time will be spent to develop this? Of course, this depends on more detailed context and I apologize for this, but consider this question generic.

For small projects, this structure is definitely an overkill. You'll lose too much time dealing with all levels of indirection, and the benefit won't pay off if the project doesn't grow, so don't bother with it if that's your case. You can benefit from a less formal structure with fewer layers and still have a good level of independence between them if you keep the discipline and consistency to maintain it organized and decoupled.

In terms of development speed for medium and large-sized projects, the initial setup time can be consuming. However, after implementing the first use case, the subsequent ones will be quick as the structure is already in place as a starting point. It took me a little less than an hour to implement all the layers (tests included) for the Category entity, as I already had implemented them for the User entity.

Regarding the development flow, a good framework to follow is to work from the inside out. For example (ignoring the tests):

  1. Entity data modeling
  2. DTO data modeling
  3. Protocols definition (i.e. the interfaces that will be used by the use cases)
  4. Use case implementation
  5. Protocols implementation (e.g. repository layer, db entities, etc)
  6. API endpoint definition, etc

Let me know if my answer makes sense to you and feel free to ask me more questions!

leonardomarcao commented 2 months ago

Thank you for answer my question and clarify my mind.

So, I decided to use your project making some adaptations, look the currently structure:

β”œβ”€β”€ alembic.ini
β”œβ”€β”€ app
β”‚Β Β  β”œβ”€β”€ api
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dependencies
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ address.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ auth.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ blog.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ company.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ crypto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ document.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ jwt.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ mail_service.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ s3_service.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ tenant.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ user.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── vehicle.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ extensions.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ middleware
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ exceptions.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ query_params.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── tenant.py
β”‚Β Β  β”‚Β Β  └── routers
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ root.py
β”‚Β Β  β”‚Β Β      └── v1
β”‚Β Β  β”œβ”€β”€ application
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ config.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ data
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── default_data.json
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── paginate.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ base.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ enum
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── __init__.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ exceptions
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ address.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ auth.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ base.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ blog.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ company.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ document.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ tenant.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ user.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── vehicle.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ i18n
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── exceptions.json
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ interfaces
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ crypto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ jwt.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ mail_service.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ repositories
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ s3.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── unit_of_work.py
β”‚Β Β  β”‚Β Β  └── setup.py
β”‚Β Β  β”œβ”€β”€ domain
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ address
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ city
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ country
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ state
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ blog
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ company
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ document
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ tenant
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ user
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── usecases.py
β”‚Β Β  β”‚Β Β  └── vehicle
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ advertisement
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ brand
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ category
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ dto.py
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ entities.py
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ feature
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β      β”œβ”€β”€ model
β”‚Β Β  β”‚Β Β      └── usecases.py
β”‚Β Β  β”œβ”€β”€ infra
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ common
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ application.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── resize_image.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ db
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ models
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ repositories
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── unit_of_work
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”œβ”€β”€ providers
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ crypto.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ data_validation.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ jwt.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  β”œβ”€β”€ mail.py
β”‚Β Β  β”‚Β Β  β”‚Β Β  └── s3.py
β”‚Β Β  β”‚Β Β  └── templates
β”‚Β Β  β”‚Β Β      └── mail
β”‚Β Β  β”œβ”€β”€ __init__.py
β”‚Β Β  └── __main__.py
β”œβ”€β”€ docker-compose.yml
β”œβ”€β”€ Dockerfile
β”œβ”€β”€ docs
β”œβ”€β”€ heroku.yml
β”œβ”€β”€ package-lock.json
β”œβ”€β”€ poetry.lock
β”œβ”€β”€ README.md
β”œβ”€β”€ scripts
β”‚Β Β  └── init.sql
└── start-dev.sh

I can consider this small today, but it's a whitelabel project that'll be grow-up after some time.

It's working 100%!

Thank you my friend.

alefeans commented 1 month ago

That's awesome! At first, I was tempted to follow something similar to what you did in the domain layer, but I decided to go with the current implementation.

Would you mind explaining the role of the application layer?