1. others
1.1. styles
1.1.1. bad
1.1.1.1. Very bad
1.1.2. good
1.1.2.1. very good
1.1.3. not as good
1.1.4. not as bad
1.1.5. important
1.1.5.1. Very important
1.1.6. warning
1.1.7. link
1.2. AUTHOR
1.2.1. Nima Shokouhfar
1.2.1.1. Linkedin
1.2.1.1.1. Follow me on LinkedIn to stay updated on my latest professional insights and tech projects!
1.2.1.2. Youtube
1.2.1.2.1. code with nima
1.2.1.2.2. ideariver
1.2.1.3. Medium
1.2.1.3.1. ✍️ Follow me on Medium to read my latest articles on tech, coding, and innovation!
1.2.1.4. Github
1.2.1.4.1. ⭐️ Give my projects a star on GitHub and explore my repositories to discover new tools and innovations!
1.2.1.4.2. 💖 Sponsor me on GitHub to support my open-source contributions and help me create even more useful projects!
1.2.1.5. upwork
1.2.1.5.1. 💼 Hire me on Upwork for freelance projects. Let’s work together to bring your tech ideas to life!
1.2.1.6. main website: ideariver.ca
1.2.1.6.1. 🚀 Visit IdeaRiver.ca for all my latest projects, blogs, and ways to connect!
1.3. Styling Version
1.3.1. 3.0.1
2. main
2.1. access json property through get
2.2. dependency injection
2.2.1. chatgpt
2.2.1.1. inject sample source code
2.3. DTO
2.4. interface
2.5. library
2.5.1. graph
2.5.1.1. NetworkX
2.5.1.1.1. course
2.6. virtual environment
2.6.1. ```bash python -m venv venv # On windows: venv\Scripts\activate # On Linux: source venv/bin/activate ```
2.6.1.1. venv\Scripts\activate
2.6.2. It is tide to the location of the project
2.6.2.1. if you chnage the location. you should delete the venv file and install everything again
2.7. create packages
2.7.1. WI
2.7.1.1. 2. Package the Project Properly (Create a Python Package)
2.7.1.1.1. Another approach is to make your plugins directory a proper Python package by adding `__init__.py` files and installing it in editable mode.
2.7.1.1.2. Steps:
2.7.1.1.3. Pros:
2.7.1.1.4. Cons:
2.7.2. PyPI
2.7.2.1. Login Credentials for Twine:
2.7.2.1.1. When you use twine to upload your package, it will prompt you for your PyPI username and password. You will use your regular PyPI login credentials (username and password) at that point.
2.8. python file structure standard practice
2.8.1. Standard Python project structure typically looks like this:
2.8.1.1. Why This Structure?
2.8.1.1.1. Package Directory (ideariver_services_python)
2.8.1.1.2. Tests Directory (tests)
2.8.1.1.3. Root Directory
2.8.1.2. Standard Practice for Testing
2.8.1.2.1. Tests should live in a tests folder, separate from package code
2.8.1.2.2. Each module or functionality has a corresponding test file, named as test_<module_name>.py
2.8.1.2.3. Tools like pytest can be used to run tests by automatically detecting these files
2.8.1.3. project_root/ ├── ideariver_services_python/ # Main package folder │ ├── __init__.py # Makes it a package │ ├── plugin_loader.py # Your plugin loader logic │ ├── plugin_rabbitmq_adapter.py # Your RabbitMQ adapter │ └── ... # Other module files ├── tests/ # Separate folder for tests │ ├── __init__.py # Makes it a package │ ├── test_plugin_loader.py # Tests for plugin loader │ ├── test_plugin_rabbitmq_adapter.py # Tests for RabbitMQ adapter ├── setup.py # Setup file for packaging ├── requirements.txt # Dependencies ├── README.md # Project documentation ├── .env # Environment variables ├── docker-compose.yml # Docker Compose setup (if using) └── .gitignore # Ignore unneeded files for git
2.9. Package manager
2.9.1. https://pypi.org/
2.9.2. get the number of downloads
2.9.2.1. https://www.pepy.tech/
2.10. requirements.txt
2.10.1. example
2.10.1.1. ```text certifi==2021.10.8 charset-normalizer==2.0.12 idna==3.3 numpy==1.21.5 pytube==12.1.0 requests==2.27.1 tqdm==4.63.0 torch==1.11.0 typing-extensions==4.1.1 whisper==1.0 pytest==7.1.2 ```
2.11. dependency injection/ IOC/ DI
2.11.1. dependency-injector
2.11.1.1. Why Dependency Injector?
2.11.1.1.1. Widespread Adoption:
2.11.1.1.2. Flexibility:
2.11.1.1.3. Production-Ready:
2.11.1.1.4. Good Documentation:
2.11.1.1.5. Testability:
2.11.1.2. installation
2.11.1.2.1. pip install dependency-injector
2.11.1.3. example
2.12. Async stuff
2.12.1. test
2.12.1.1. use
2.12.1.1.1. pytest-asyncio
2.12.1.2. async and await are the same
2.12.1.2.1. async def start_consuming(self): """Start consuming messages asynchronously.""" await self.task_queue.consume(self.process_message) print(f"Waiting for messages on queue '{self.task_queue.name}'...")
2.12.1.3. example
2.12.1.3.1. async def rabbitmq_adapter(): topic_mapping = TopicMapping( topics={"taskQueue": "task_queue", "responseQueue": "response_queue"} ) plugin_loader = PluginLoader(DummyPluginLocator()) adapter = PluginRabbitMQAdapter( rabbitmq_url="amqp://guest:guest@localhost:5672/", topic_mapping=topic_mapping, plugin_loader=plugin_loader, ) await adapter.connect() yield adapter await adapter.close()
2.12.1.4. update the pytest.ini too
2.12.1.4.1. [pytest] pythonpath = . asyncio_mode = auto asyncio_default_fixture_loop_scope = function
2.13. pytest
2.13.1. pytest.ini
2.13.1.1. example
2.13.1.1.1. [pytest] pythonpath = . asyncio_mode = auto asyncio_default_fixture_loop_scope = function
2.13.2. after all version of python
2.13.2.1. yield adapter await adapter.close()
2.13.2.1.1. @pytest.fixture(scope="function") async def rabbitmq_adapter(): topic_mapping = TopicMapping( topics={"taskQueue": "task_queue", "responseQueue": "response_queue"} ) plugin_loader = PluginLoader(DummyPluginLocator()) adapter = PluginRabbitMQAdapter( rabbitmq_url="amqp://guest:guest@localhost:5672/", topic_mapping=topic_mapping, plugin_loader=plugin_loader, ) await adapter.connect() # Declare the queues with the correct settings # await adapter.channel.declare_queue(topic_mapping.topics["taskQueue"], durable=True) # await adapter.channel.declare_queue(topic_mapping.topics["responseQueue"], durable=True) yield adapter await adapter.close()
2.14. __init__.py
2.14.1. example
2.15. Commands
2.15.1. pip freeze > requirements.txt
2.15.1.1. generate dependencies
2.15.2. virtual environment stuff
2.15.2.1. python -m venv venv
2.15.2.1.1. init the virtual environment
2.15.2.2. venv\Scripts\activate # On Linux: source venv/bin/activate
2.15.2.2.1. start the virtual environment
2.15.3. pip install pytube
2.15.4. test
2.15.4.1. pytest test_download.py
2.15.4.2. pytest -s test_transcribe.py
2.15.4.2.1. with kind of logs
2.15.5. python setup.py sdist
2.15.5.1. Package the Code Locally Run the following command to package your project:
2.15.6. pip install -e .
2.15.6.1. Install the Package Locally: After setting up setup.py, run the following command in your terminal to install the package locally in development mode:
2.15.7. upgrade to the latest package
2.15.7.1. pip install --upgrade --force-reinstall ideariver_core
2.15.8. deleting all cache files
2.15.8.1. find . -name '__pycache__' -exec rm -rf {} + find . -name '*.pyc' -delete
2.15.9. Legacy
2.15.9.1. Test
2.15.9.1.1. test a specefic test
2.15.9.1.2. pytest is another alternative
2.15.9.1.3. For async stuff use
2.15.9.2. run code
2.15.9.3. install
2.15.9.3.1. with logo
2.15.9.4. script to exe conversion
2.15.9.5. Install the Package Locally: After setting up setup.py, run the following command in your terminal to install the package locally in development mode:
2.15.9.5.1. pip install -e .
2.16. My general thought on python
2.16.1. pro/cons
2.16.1.1. the good
2.16.1.1.1. for processing stuff, it has reall a rich ecosystem
2.16.1.1.2. It is very chatgpt friendly
2.16.1.1.3. for simple stuff, I love it
2.16.1.2. the bad
2.16.1.2.1. for something complex, I am against it
2.16.2. But at scale, you have no choice, you should do this for plugin systems.
2.16.2.1. Because of adaptation and the rich ecosystem