Compare commits

...
111 Commits
Author SHA1 Message Date
MervinPraison a432135e75 chore: update praisonai package version from 2.2.33 to 2.2.34 across Docker and deployment files 2025-06-21 07:22:29 +01:00
MervinPraison 17e620d9e0 refactor: migrate workflow process to sequential and enhance result handling with debug logging 2025-06-21 07:19:34 +01:00
MervinPraison 17ceaad435 Merge branch 'main' of https://github.com/MervinPraison/PraisonAI 2025-06-21 06:40:45 +01:00
MervinPraison fe3ba3a916 feat: add weather server and Ollama LLM integration with test files 2025-06-21 06:40:44 +01:00
Mervin Praison 1b9c9b78c9 Merge pull request #670 from DhivyaBharathy-web/add-Meta_LLaMA3_SyntheticData
Add  Meta Synthetic Data Generator (LLaMA 3.2 - 3B)
2025-06-20 23:53:33 +02:00
Mervin Praison 1051f3a705 Merge pull request #671 from DhivyaBharathy-web/add-Sesame_CSM_1B_TTS
Add  Sesame CSM (1B) - TTS Model
2025-06-20 23:53:18 +02:00
Mervin Praison 982473ce08 Merge pull request #673 from DhivyaBharathy-web/add-KnowledgeAgent_PraisonAI
Add knowledge agent praison ai
2025-06-20 23:52:59 +02:00
DhivyaBharathy 09de1f1405 Add files via upload 2025-06-20 10:18:42 +05:30
DhivyaBharathy ee21add0ef Delete examples/cookbooks/KnowledgeAgent_PraisonAI.ipynb 2025-06-20 10:18:01 +05:30
DhivyaBharathy dcc2f899e7 Add files via upload 2025-06-20 10:16:59 +05:30
DhivyaBharathy 362d6e62be Add files via upload 2025-06-18 13:14:09 +05:30
DhivyaBharathy-web d2a12c5fc6 Add Sesame_CSM_1B_TTS notebook 2025-06-18 07:37:58 +00:00
DhivyaBharathy-web 993c342209 Add Meta_LLaMA3_SyntheticData notebook 2025-06-18 07:36:01 +00:00
MervinPraison 218370fef8 Merge branch 'main' of https://github.com/MervinPraison/PraisonAI 2025-06-17 11:09:41 +01:00
MervinPraison 117969e8f6 Update Claude workflow to simplify action references by using version tags, enhancing clarity and maintainability. 2025-06-17 11:09:40 +01:00
DhivyaBharathy aa3282cabd Add files via upload 2025-06-17 15:29:02 +05:30
Mervin Praison 914532028d Merge pull request #669 from DhivyaBharathy-web/add-Phi_3_Medium_Conversational
Add Phi_3_Medium_Conversational notebook
2025-06-17 11:56:33 +02:00
DhivyaBharathy-web 83d808ddc1 Add Phi_3_Medium_Conversational notebook 2025-06-17 09:54:35 +00:00
Mervin Praison 3cf922f36c Merge pull request #667 from DhivyaBharathy-web/add-Phi_4_14B_GRPO
Add Phi_4_14B_GRPO notebook
2025-06-17 11:52:37 +02:00
Mervin Praison b5956e0d39 Merge pull request #668 from DhivyaBharathy-web/add-Phi_3_5_Mini_Conversational
Add Phi_3_5_Mini_Conversational notebook
2025-06-17 11:52:27 +02:00
Mervin Praison 07952d1b61 Merge pull request #666 from DhivyaBharathy-web/add-Phi_4_Conversational
Add Phi_4_Conversational notebook
2025-06-17 11:52:17 +02:00
DhivyaBharathy-web 9eedd55b19 Add Phi_3_5_Mini_Conversational notebook 2025-06-17 09:49:45 +00:00
DhivyaBharathy-web 3b31afb270 Add Phi_4_14B_GRPO notebook 2025-06-17 09:45:50 +00:00
DhivyaBharathy-web c77f3c7363 Add Phi_4_Conversational notebook 2025-06-17 09:40:28 +00:00
Mervin Praison c808ce29e4 Merge pull request #632 from DhivyaBharathy-web/add-qwen-chatbot-agent
Add qwen chatbot agent
2025-06-17 00:24:41 +02:00
Mervin Praison ca70d34ffe Merge pull request #659 from DhivyaBharathy-web/add-llama3-2-11b-vision-agent
Add llama3 2 11b vision agent
2025-06-17 00:20:23 +02:00
Mervin Praison 96563ffb04 Merge pull request #662 from DhivyaBharathy-web/add-Pixtral_12B_Vision_Model
Add pixtral 12 b vision model
2025-06-17 00:20:11 +02:00
Mervin Praison d7a89a5b5d Merge pull request #663 from DhivyaBharathy-web/add-Qwen2-5-VL_7B_Vision_Model
Add qwen2 5 vl 7 b vision model
2025-06-17 00:20:02 +02:00
DhivyaBharathy-web 7d0afb062e Resolve conflict by deleting Mistral notebook 2025-06-16 11:44:20 +00:00
DhivyaBharathy-web 3ede63d3d9 Resolve conflict by deleting Mistral notebook 2025-06-16 11:30:59 +00:00
DhivyaBharathy-web db58770b46 Resolve conflict by deleting Mistral notebook 2025-06-16 11:11:32 +00:00
MervinPraison 9066668121 Refactor Claude Code Action to streamline prompt handling by reading directly from the prompt file, enhancing clarity and efficiency in command execution. 2025-06-16 09:57:01 +01:00
MervinPraison 8e5b6a9d38 Refactor Claude Code Action by removing unnecessary timeout and custom instructions handling, streamlining command argument preparation for improved clarity and efficiency. 2025-06-16 09:41:00 +01:00
MervinPraison b16086c17d Update Claude Code Action to enhance input options and streamline prompt extraction from GitHub context. Remove redundant GitHub token and MCP installation steps in workflow for improved clarity and efficiency. 2025-06-16 09:39:06 +01:00
MervinPraison f50a2448df Refactor Claude Code Action to auto-generate prompts from GitHub context when no input is provided, improving usability and functionality. Update workflow to remove redundant prompt generation step, streamlining the process. 2025-06-16 09:13:23 +01:00
MervinPraison b1ff7a9500 Update GitHub Actions workflow by standardising GitHub token reference and adding a step to generate prompts from GitHub context, enhancing functionality and clarity. 2025-06-16 09:10:37 +01:00
DhivyaBharathy c4829d45a4 Merge branch 'main' into add-qwen-chatbot-agent 2025-06-16 13:04:42 +05:30
DhivyaBharathy f4479fa1f4 Add files via upload 2025-06-16 13:00:35 +05:30
DhivyaBharathy-web f008aa1c3b Add Qwen2.5-VL_7B_Vision_Model Agent notebook 2025-06-16 07:20:55 +00:00
MervinPraison 3abb084209 Refactor Claude Code Action by consolidating functionality into a composite action, removing Dockerfile and entrypoint script, and enhancing input descriptions for clarity and usability. 2025-06-16 08:16:05 +01:00
DhivyaBharathy-web 617efcc96d Add LLaMA3-2_11B_Vision Agent notebook 2025-06-16 07:15:16 +00:00
MervinPraison 41bec67b51 Refine Claude workflow by directly executing the 'claude' script with Node to bypass BusyBox environment issues, enhancing reliability in CI execution. 2025-06-16 07:59:11 +01:00
MervinPraison 91361eee17 Enhance Claude workflow by adding debugging steps for environment verification, checking for the presence of the 'claude' command, and implementing automatic installation if not found, ensuring smoother execution in CI mode. 2025-06-16 07:56:35 +01:00
MervinPraison aa1356629b Update Claude workflow by modifying Docker image reference format, enhancing environment variable debugging, and updating GitHub token reference for improved clarity and reliability. 2025-06-16 07:54:53 +01:00
MervinPraison ac86a8dd76 Fix GHCR authentication issue in Claude workflow by updating login method and adding a logout step for improved reliability. 2025-06-16 07:50:37 +01:00
MervinPraison ab679e040e Add Docker pull test step to Claude workflow for verification of successful image retrieval after login. 2025-06-16 07:49:57 +01:00
MervinPraison c2fded7a89 Refactor Claude workflow by removing redundant debugging and testing steps, updating GitHub token usage for improved security and clarity. 2025-06-16 07:45:03 +01:00
Mervin Praison 4966ec1ae1 Merge pull request #658 from MervinPraison/develop
Enhance Claude workflow by adding environment variable for GitHub tok…
2025-06-16 08:26:16 +02:00
MervinPraison c31870a991 Enhance Claude workflow by adding environment variable for GitHub token and implementing package visibility check and Docker authentication tests for improved reliability and security. 2025-06-16 07:25:57 +01:00
Mervin Praison 67f4a89062 Merge pull request #657 from MervinPraison/develop
Add debugging steps to Claude workflow for environment verification a…
2025-06-16 08:24:07 +02:00
MervinPraison a898bbb7d1 Add debugging steps to Claude workflow for environment verification and Docker testing 2025-06-16 07:23:50 +01:00
Mervin Praison 107d33deb7 Merge pull request #656 from MervinPraison/develop
Update Claude Code action to restrict package permissions and remove …
2025-06-16 08:21:21 +02:00
MervinPraison 9d963e4eeb Update Claude Code action to restrict package permissions and remove Docker image build step for streamlined workflow. 2025-06-16 07:21:02 +01:00
Mervin Praison 56b296b8d6 Merge pull request #655 from MervinPraison/develop
Update Claude Code action to enable package writing and add Docker im…
2025-06-16 08:18:07 +02:00
MervinPraison fddf999688 Update Claude Code action to enable package writing and add Docker image build and push step for enhanced deployment capabilities. 2025-06-16 07:14:29 +01:00
Mervin Praison 6374aba783 Merge pull request #654 from MervinPraison/develop
Update Claude Code action to use GitHub token for authentication, enh…
2025-06-16 08:13:03 +02:00
MervinPraison 9408d699e8 Update Claude Code action to use GitHub token for authentication, enhancing security and consistency in the workflow. 2025-06-16 07:12:10 +01:00
Mervin Praison 6358671ab9 Merge pull request #652 from MervinPraison/develop
Enhance Claude Code action by adding environment variable verificatio…
2025-06-15 07:43:51 +02:00
MervinPraison f5bd55bb9a Enhance Claude Code action by adding environment variable verification and updating Docker setup for improved reliability 2025-06-15 06:43:34 +01:00
Mervin Praison a93c571f33 Merge pull request #651 from MervinPraison/develop
Update Claude Code action reference to use local action for improved …
2025-06-15 07:42:13 +02:00
MervinPraison 8ea0e4c831 Update Claude Code action reference to use local action for improved maintainability 2025-06-15 06:41:42 +01:00
Mervin Praison 8a1dc24794 Merge pull request #650 from MervinPraison/develop
Update Claude Code action reference to use quotes for consistency
2025-06-15 07:39:30 +02:00
MervinPraison b331229578 Update Claude Code action reference to use quotes for consistency 2025-06-15 06:39:12 +01:00
Mervin Praison 7af52735cf Merge pull request #649 from MervinPraison/develop
Add GitHub Container Registry login step and update Claude Code actio…
2025-06-15 07:37:42 +02:00
MervinPraison 2902fec42e Add GitHub Container Registry login step and update Claude Code action reference 2025-06-15 06:37:28 +01:00
Mervin Praison 64f752a8e0 Merge pull request #648 from MervinPraison/develop
Update Docker image reference in Claude Code action for consistency
2025-06-15 07:35:30 +02:00
MervinPraison d994fb5047 Update Docker image reference in Claude Code action for consistency 2025-06-15 06:34:52 +01:00
Mervin Praison 760fb9530b Merge pull request #647 from MervinPraison/develop
Refactor Claude Code integration to use local action instead of Docke…
2025-06-15 07:33:04 +02:00
MervinPraison de165975b0 Refactor Claude Code integration to use local action instead of Docker image for improved maintainability 2025-06-15 06:32:43 +01:00
Mervin Praison dfd74a2fe7 Merge pull request #646 from MervinPraison/develop
Develop
2025-06-15 07:29:30 +02:00
MervinPraison 9265ca08a2 Update Claude Code integration to use Docker image and add GitHub token for authentication 2025-06-15 06:28:57 +01:00
MervinPraison 665df753fd Remove CLAUDE_CODE_INTEGRATION_PRAISONAI_AGENTS.md as it is no longer needed for the integration of Claude Code with PraisonAI Agents. This deletion simplifies the documentation and reflects the current state of the project. 2025-06-15 05:55:55 +01:00
Mervin Praison 94d991f4ec Merge pull request #643 from MervinPraison/develop
Update PraisonAI and dependencies to version 2.2.33
2025-06-14 08:45:31 +02:00
MervinPraison 632cf68423 Update PraisonAI and dependencies to version 2.2.33
- Updated PraisonAI version from 2.2.32 to 2.2.33 across multiple Dockerfiles and relevant files.
- Adjusted dependency versions in pyproject.toml and other files for consistency.
- Enhanced README documentation to reflect the updated version.

This change integrates the latest features and improvements from PraisonAI while ensuring compatibility with existing code.
2025-06-14 07:45:15 +01:00
Mervin Praison d956c605f7 Merge pull request #635 from MervinPraison/claude/issue-634-20250610_115418
feat: Refactor Claude Code integration to use PraisonAI Agents
2025-06-14 08:43:35 +02:00
Mervin Praison 7e3de10f32 Rename test_claude_code_integration.py to src/praisonai/tests/unit/test_claude_code_integration.py 2025-06-14 07:41:20 +01:00
Mervin Praison 79883f1af2 Merge pull request #642 from MervinPraison/develop
Update PraisonAI and dependencies to version 2.2.32
2025-06-14 08:39:04 +02:00
MervinPraison a098eb0150 Update PraisonAI and dependencies to version 2.2.32
- Updated PraisonAI version from 2.2.31 to 2.2.32 across multiple Dockerfiles and relevant files.
- Adjusted dependency versions in pyproject.toml and other files for consistency.
- Enhanced README documentation to reflect the updated version.

This change integrates the latest features and improvements from PraisonAI while ensuring compatibility with existing code.
2025-06-14 07:38:45 +01:00
Mervin Praison b9ce3b4ccb Merge pull request #641 from MervinPraison/develop
Allow to configure reflection prompt
2025-06-14 08:36:28 +02:00
claude[bot]andMervin Praison 58b44280df feat: add self-reflection support with configurable prompt to achat method
- Implement complete self-reflection logic in achat method to match chat method
- Support configurable reflect_prompt parameter in async operations  
- Add reflection loop with min/max limits and error handling
- Update method docstring to reflect new self-reflection capability
- Ensure consistent behavior between chat and achat methods

Co-authored-by: Mervin Praison <[email protected]>
2025-06-14 06:26:49 +00:00
MervinPraison 4dba09d6b1 Merge remote-tracking branch 'leo-origin/feature/add-reflection-prompt' into test-reflection-prompt 2025-06-14 07:20:09 +01:00
Mervin Praison a538513bec Merge pull request #640 from MervinPraison/develop
Develop
2025-06-14 08:17:26 +02:00
MervinPraison 4fb79207cf Merge branch 'main' of https://github.com/MervinPraison/PraisonAI into develop 2025-06-14 07:16:44 +01:00
MervinPraison 0b444fae34 Merge branch 'develop' of https://github.com/MervinPraison/PraisonAI into develop 2025-06-14 07:16:26 +01:00
MervinPraison bd34e45bbc Update PraisonAI and dependencies to version 2.2.31
- Updated PraisonAI version from 2.2.30 to 2.2.31 across multiple Dockerfiles and the Ruby formula.
- Adjusted dependency versions in pyproject.toml and other relevant files for consistency.
- Enhanced README documentation to reflect the updated version.

This change ensures that the latest features and improvements from PraisonAI are integrated while maintaining compatibility with existing code.
2025-06-14 07:16:25 +01:00
Mervin Praison f4f051e57e Merge pull request #638 from krkead/patch-2
Update chainlit_ui.py to work with newer chainlit versions
2025-06-14 08:13:56 +02:00
Mervin Praison 3c2610cc3c Merge pull request #639 from krkead/patch-1
Update agents.py to work with newer chainlit versions
2025-06-14 08:13:44 +02:00
krkead 9788454134 Update chainlit_ui.py to work with newer chainlit versions
The previous payload modification was incorrect
2025-06-13 18:04:52 -03:00
krkead e618004e60 Update agents.py to work with newer chainlit versions 2025-06-13 18:02:35 -03:00
Mervin Praison 384803ba8e Merge pull request #637 from DhivyaBharathy-web/add-mistral-agent
Add Mistral v0.3 Conversational Agent – Conceptual Workflow
2025-06-12 06:01:21 +02:00
DhivyaBharathy 1a306988cf Delete examples/cookbooks/Mistral_v0_3_Conversational_Demo.ipynb 2025-06-11 16:22:41 +05:30
DhivyaBharathy-web d3bb366a51 Add Mistral 7B Instruction Agent notebook 2025-06-11 10:49:16 +00:00
DhivyaBharathy e579e84b52 Add files via upload 2025-06-11 16:13:42 +05:30
leovs09 61440403f5 add agent constructor params description 2025-06-11 00:48:51 +02:00
leovs09 b615782175 Allow to configure reflection prompt 2025-06-11 00:24:59 +02:00
claude[bot]andMervinPraison 35199979f0 feat: Refactor Claude Code integration to use PraisonAI Agents
- Replace litellm direct usage with praisonaiagents framework
- Implement Claude Code as a custom tool that agents can decide to use
- Add --claudecode CLI flag support: `praisonai code --claudecode`
- Create intelligent agent that chooses when to use Claude Code vs regular responses
- Maintain full backward compatibility with litellm fallback
- Add UI toggle switch for enabling/disabling Claude Code
- Implement git operations with automatic branch creation and PR URLs
- Add comprehensive error handling and streaming support
- Include test script and detailed documentation

Key improvements:
- Agent-driven decision making instead of manual detection logic
- Better tool coordination and flexibility
- Minimal code changes with maintained compatibility
- Enhanced user experience with intelligent tool selection

Co-Authored-By: MervinPraison <[email protected]>
2025-06-10 12:02:19 +00:00
DhivyaBharathy eeb77cfd20 Add files via upload 2025-06-10 16:15:43 +05:30
Mervin Praison 00d7994601 Merge pull request #633 from DhivyaBharathy-web/add-nlp-asr-agent
Add NLP + ASR Agent (Official BERT Large + Whisper Large V3)
2025-06-10 08:55:08 +01:00
DhivyaBharathy 10aa49addc Merge branch 'main' into add-nlp-asr-agent 2025-06-10 12:05:50 +05:30
DhivyaBharathy-web 79c9cf8bf9 Add NLP + ASR Agent (Official BERT Large + Whisper Large V3) notebook 2025-06-10 06:32:31 +00:00
DhivyaBharathy f4cb62a288 Merge branch 'main' into add-qwen-chatbot-agent 2025-06-10 11:55:04 +05:30
DhivyaBharathy dde6ec4a6a Update qwen_colab_agent.ipynb 2025-06-10 11:52:40 +05:30
DhivyaBharathy-web c8b2414f5b Add Qwen Agent notebook 2025-06-10 06:17:23 +00:00
Mervin Praison a9416fb7fc Merge pull request #631 from MervinPraison/claude/issue-630-20250609_145612
feat: add remote agent connectivity with Google ADK-like API
2025-06-09 20:43:47 +01:00
Mervin Praison 547b40ee72 Rename test_remote_agent.py to src/praisonai/tests/unit/test_remote_agent.py 2025-06-09 20:43:32 +01:00
claude[bot]andMervinPraison 4fc35d1b10 feat: add remote agent connectivity with Google ADK-like API
- Enhanced Session class to support remote agent URLs
- Added agent_url parameter for direct agent connectivity  
- Implemented HTTP client for remote agent communication
- Added connection testing and validation
- Provided send_message() alias for Google ADK compatibility
- Created comprehensive examples and documentation
- Maintained full backward compatibility
- Added proper error handling for remote operations

Fixes #630

Co-authored-by: MervinPraison <[email protected]>
2025-06-09 15:02:42 +00:00
Mervin Praison c72d74987b Merge pull request #625 from DhivyaBharathy-web/add-mistral7b-agent
Add mistral7b agent
2025-06-08 00:14:37 +01:00
DhivyaBharathy 430ec6571a Update MistralTechAgent.ipynb 2025-06-07 14:22:57 +05:30
DhivyaBharathy e88288773a Add files via upload 2025-06-07 14:15:47 +05:30
DhivyaBharathy-web 9af03e3fef Add Mistral-7B-Instruct-v0.1 Instruction Agent notebook 2025-06-07 08:43:22 +00:00
DhivyaBharathy 1d22818662 Add files via upload 2025-06-06 15:28:14 +05:30
52 changed files with 23749 additions and 4753 deletions

No files matched your search

+34
View File
@@ -0,0 +1,34 @@
---
name: Bug report
about: Create a report to help us improve
title: '[BUG] '
labels: bug
assignees: ''
---
## Environment
- Provider (select one):
- [ ] Anthropic
- [ ] OpenAI
- [ ] Google Vertex AI
- [ ] AWS Bedrock
- [ ] Other: <!-- specify -->
- PraisonAI version: <!-- if known -->
- Operating System: <!-- e.g. macOS 14.3, Windows 11, Ubuntu 22.04 -->
## Full Code
<!-- Full code that reproduces the bug -->
## Steps to Reproduce
1. <!-- First step -->
2. <!-- Second step -->
3. <!-- And so on... -->
## Expected Behavior
<!-- What you expected to happen -->
## Actual Behavior
<!-- What actually happened -->
## Additional Context
<!-- Add any other context about the problem here, such as screenshots, logs, etc. -->
@@ -0,0 +1,240 @@
name: "Claude Code Action"
description: "Run Claude Code in GitHub Actions workflows"
inputs:
anthropic_api_key:
description: "Anthropic API key"
required: false
github_token:
description: "GitHub token for Claude to operate with"
required: false
default: ${{ github.token }}
trigger_phrase:
description: "The trigger phrase to look for in comments, issue/PR bodies, and issue titles"
required: false
default: "@claude"
assignee_trigger:
description: "The assignee username that triggers the action (e.g. @claude). Only used for issue assignment"
required: false
max_turns:
description: "Maximum number of conversation turns Claude can take"
required: false
timeout_minutes:
description: "Timeout in minutes for execution"
required: false
default: "30"
model:
description: "Model to use (provider-specific format required for Bedrock/Vertex)"
required: false
use_bedrock:
description: "Use Amazon Bedrock with OIDC authentication instead of direct Anthropic API"
required: false
default: "false"
use_vertex:
description: "Use Google Vertex AI with OIDC authentication instead of direct Anthropic API"
required: false
default: "false"
allowed_tools:
description: "Additional tools for Claude to use (the base GitHub tools will always be included)"
required: false
default: ""
disallowed_tools:
description: "Tools that Claude should never use"
required: false
default: ""
custom_instructions:
description: "Additional custom instructions to include in the prompt for Claude"
required: false
default: ""
mcp_config:
description: "Additional MCP configuration (JSON string) that merges with the built-in GitHub MCP servers"
required: false
default: ""
claude_env:
description: "Custom environment variables to pass to Claude Code execution (YAML format)"
required: false
default: ""
direct_prompt:
description: "Direct prompt for Claude to execute automatically without needing a trigger (for automated workflows)"
required: false
runs:
using: "composite"
steps:
- name: Install Claude Code
shell: bash
run: npm install -g @anthropic-ai/claude-code
- name: Install GitHub MCP Server
shell: bash
run: |
claude mcp add-json github '{
"command": "docker",
"args": [
"run",
"-i",
"--rm",
"-e",
"GITHUB_PERSONAL_ACCESS_TOKEN",
"ghcr.io/github/github-mcp-server:sha-ff3036d"
],
"env": {
"GITHUB_PERSONAL_ACCESS_TOKEN": "${{ inputs.github_token }}"
}
}'
- name: Extract GitHub Context and Create Prompt
shell: bash
id: prepare_context
run: |
echo "🔍 Extracting GitHub context from event: ${{ github.event_name }}"
# Function to check for trigger phrase
check_trigger() {
local text="$1"
local trigger="${{ inputs.trigger_phrase }}"
if [[ "$text" == *"$trigger"* ]]; then
return 0
fi
return 1
}
# Extract context based on event type
TRIGGER_FOUND="false"
USER_REQUEST=""
CONTEXT_INFO=""
case "${{ github.event_name }}" in
"issue_comment")
COMMENT_BODY="${{ github.event.comment.body }}"
ISSUE_TITLE="${{ github.event.issue.title }}"
ISSUE_NUMBER="${{ github.event.issue.number }}"
if check_trigger "$COMMENT_BODY"; then
TRIGGER_FOUND="true"
USER_REQUEST="$COMMENT_BODY"
CONTEXT_INFO="Issue Comment on #$ISSUE_NUMBER: $ISSUE_TITLE"
fi
;;
"pull_request_review_comment")
COMMENT_BODY="${{ github.event.comment.body }}"
PR_TITLE="${{ github.event.pull_request.title }}"
PR_NUMBER="${{ github.event.pull_request.number }}"
if check_trigger "$COMMENT_BODY"; then
TRIGGER_FOUND="true"
USER_REQUEST="$COMMENT_BODY"
CONTEXT_INFO="PR Comment on #$PR_NUMBER: $PR_TITLE"
fi
;;
"pull_request_review")
REVIEW_BODY="${{ github.event.review.body }}"
PR_TITLE="${{ github.event.pull_request.title }}"
PR_NUMBER="${{ github.event.pull_request.number }}"
if check_trigger "$REVIEW_BODY"; then
TRIGGER_FOUND="true"
USER_REQUEST="$REVIEW_BODY"
CONTEXT_INFO="PR Review on #$PR_NUMBER: $PR_TITLE"
fi
;;
"issues")
ISSUE_BODY="${{ github.event.issue.body }}"
ISSUE_TITLE="${{ github.event.issue.title }}"
ISSUE_NUMBER="${{ github.event.issue.number }}"
if check_trigger "$ISSUE_TITLE" || check_trigger "$ISSUE_BODY"; then
TRIGGER_FOUND="true"
USER_REQUEST="$ISSUE_BODY"
CONTEXT_INFO="Issue #$ISSUE_NUMBER: $ISSUE_TITLE"
elif [[ "${{ github.event.action }}" == "assigned" && -n "${{ inputs.assignee_trigger }}" ]]; then
ASSIGNEE="${{ github.event.assignee.login }}"
if [[ "$ASSIGNEE" == "${{ inputs.assignee_trigger }}" ]]; then
TRIGGER_FOUND="true"
USER_REQUEST="$ISSUE_BODY"
CONTEXT_INFO="Issue #$ISSUE_NUMBER assigned to $ASSIGNEE: $ISSUE_TITLE"
fi
fi
;;
esac
# Check for direct prompt override
if [[ -n "${{ inputs.direct_prompt }}" ]]; then
TRIGGER_FOUND="true"
USER_REQUEST="${{ inputs.direct_prompt }}"
CONTEXT_INFO="Automated GitHub workflow"
fi
if [[ "$TRIGGER_FOUND" != "true" ]]; then
echo "❌ No trigger phrase found or direct prompt provided. Exiting gracefully."
echo "SKIP_EXECUTION=true" >> $GITHUB_ENV
exit 0
fi
echo "✅ Trigger found! Context: $CONTEXT_INFO"
# Create comprehensive prompt
mkdir -p /tmp/claude-action
cat > /tmp/claude-action/github-context-prompt.txt << EOF
You are Claude Code, an AI assistant helping with GitHub workflows and code.
Repository: ${{ github.repository }}
Context: $CONTEXT_INFO
Event: ${{ github.event_name }}
User Request:
$USER_REQUEST
Please analyze the request and provide helpful assistance. You have access to repository tools and can help with:
- Code analysis and implementation
- GitHub workflows and automation
- Pull request reviews and feedback
- Issue resolution and bug fixes
- Documentation updates
- Testing and deployment
Respond naturally and helpfully to the user's request using the available tools.
EOF
echo "PROMPT_FILE=/tmp/claude-action/github-context-prompt.txt" >> $GITHUB_ENV
echo "SKIP_EXECUTION=false" >> $GITHUB_ENV
- name: Run Claude Code
if: env.SKIP_EXECUTION != 'true'
shell: bash
run: |
echo "🚀 Running Claude Code with GitHub context..."
# Build command arguments
CMD_ARGS=("-p" "--verbose" "--output-format" "stream-json")
# Add max turns if specified
if [[ -n "${{ inputs.max_turns }}" ]]; then
CMD_ARGS+=("--max-turns" "${{ inputs.max_turns }}")
fi
# Add allowed tools (include GitHub tools by default)
TOOLS="mcp__github__get_issue,mcp__github__get_issue_comments,mcp__github__update_issue,mcp__github__search_issues,mcp__github__list_issues,mcp__github__create_comment,Read,Write,Edit,Bash"
if [[ -n "${{ inputs.allowed_tools }}" ]]; then
TOOLS="$TOOLS,${{ inputs.allowed_tools }}"
fi
CMD_ARGS+=("--allowedTools" "$TOOLS")
# Add disallowed tools
if [[ -n "${{ inputs.disallowed_tools }}" ]]; then
CMD_ARGS+=("--disallowedTools" "${{ inputs.disallowed_tools }}")
fi
echo "📝 Executing Claude Code with prompt from file..."
# Execute Claude Code with timeout, using stdin for the prompt
TIMEOUT_SECONDS=$((${{ inputs.timeout_minutes }} * 60))
timeout $TIMEOUT_SECONDS claude "${CMD_ARGS[@]}" < "${{ env.PROMPT_FILE }}"
echo "✅ Claude Code execution completed"
env:
ANTHROPIC_API_KEY: ${{ inputs.anthropic_api_key }}
GITHUB_TOKEN: ${{ inputs.github_token }}
@@ -0,0 +1,87 @@
name: "Claude Issue Triage Action"
description: "Automatically triage GitHub issues using Claude Code"
inputs:
timeout_minutes:
description: "Timeout in minutes for execution"
required: false
default: "5"
anthropic_api_key:
description: "Anthropic API key"
required: true
github_token:
description: "GitHub token with repo and issues permissions"
required: true
runs:
using: "composite"
steps:
- name: Checkout repository code
uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Create prompt file
shell: bash
run: |
mkdir -p /tmp/claude-prompts
cat > /tmp/claude-prompts/claude-issue-triage-prompt.txt << 'EOF'
You're an issue triage assistant for GitHub issues. Your task is to analyze the issue and select appropriate labels from the provided list.
IMPORTANT: Don't post any comments or messages to the issue. Your only action should be to apply labels.
Issue Information:
- REPO: ${{ github.repository }}
- ISSUE_NUMBER: ${{ github.event.issue.number }}
TASK OVERVIEW:
1. First, fetch the list of labels available in this repository by running: `gh label list`. Run exactly this command with nothing else.
2. Next, use the GitHub tools to get context about the issue:
- You have access to these tools:
- mcp__github__get_issue: Use this to retrieve the current issue's details including title, description, and existing labels
- mcp__github__get_issue_comments: Use this to read any discussion or additional context provided in the comments
- mcp__github__update_issue: Use this to apply labels to the issue (do not use this for commenting)
- mcp__github__search_issues: Use this to find similar issues that might provide context for proper categorization and to identify potential duplicate issues
- mcp__github__list_issues: Use this to understand patterns in how other issues are labeled
- Start by using mcp__github__get_issue to get the issue details
3. Analyze the issue content, considering:
- The issue title and description
- The type of issue (bug report, feature request, question, etc.)
- Technical areas mentioned
- Severity or priority indicators
- User impact
- Components affected
4. Select appropriate labels from the available labels list provided above:
- Choose labels that accurately reflect the issue's nature
- Be specific but comprehensive
- Select priority labels if you can determine urgency (high-priority, med-priority, or low-priority)
- Consider platform labels (android, ios) if applicable
- If you find similar issues using mcp__github__search_issues, consider using a "duplicate" label if appropriate. Only do so if the issue is a duplicate of another OPEN issue.
5. Apply the selected labels:
- Use mcp__github__update_issue to apply your selected labels
- DO NOT post any comments explaining your decision
- DO NOT communicate directly with users
- If no labels are clearly applicable, do not apply any labels
IMPORTANT GUIDELINES:
- Be thorough in your analysis
- Only select labels from the provided list above
- DO NOT post any comments to the issue
- Your ONLY action should be to apply labels using mcp__github__update_issue
- It's okay to not add any labels if none are clearly applicable
EOF
- name: Run Claude Code
uses: ./.github/actions/claude-code-action
with:
prompt_file: /tmp/claude-prompts/claude-issue-triage-prompt.txt
allowed_tools: "Bash(gh label list),mcp__github__get_issue,mcp__github__get_issue_comments,mcp__github__update_issue,mcp__github__search_issues,mcp__github__list_issues"
install_github_mcp: "true"
timeout_minutes: ${{ inputs.timeout_minutes }}
anthropic_api_key: ${{ inputs.anthropic_api_key }}
github_token: ${{ inputs.github_token }}
+40
View File
@@ -0,0 +1,40 @@
name: Build Claude Code Image
on:
workflow_dispatch:
inputs:
version:
description: 'Image version tag'
required: true
default: 'latest'
jobs:
build:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3
- name: Login to GitHub Container Registry
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GH_TOKEN }}
- name: Build and push Docker image
uses: docker/build-push-action@v5
with:
context: ./.github/actions/claude-code-action
push: true
platforms: linux/amd64
tags: ghcr.io/mervinpraison/praisonai-claudecode:${{ inputs.version }}
cache-from: type=gha
cache-to: type=gha,mode=max
provenance: false
+23
View File
@@ -0,0 +1,23 @@
name: Claude Issue Triage
description: "Automatically triage GitHub issues using Claude Code"
on:
issues:
types: [opened]
jobs:
triage-issue:
runs-on: ubuntu-latest
timeout-minutes: 10
permissions:
contents: read
issues: write
steps:
- name: Checkout repository
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4
- name: Run Claude Issue Triage
uses: ./.github/actions/claude-issue-triage-action
with:
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
github_token: ${{ secrets.GITHUB_TOKEN }}
+1 -2
View File
@@ -33,5 +33,4 @@ jobs:
id: claude
uses: anthropics/claude-code-action@beta
with:
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
+1 -1
View File
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
# Install Python packages (using latest versions)
RUN pip install --no-cache-dir \
flask \
"praisonai>=2.2.31" \
"praisonai>=2.2.34" \
"praisonai[api]" \
gunicorn \
markdown
+1 -1
View File
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
# Install Python packages (using latest versions)
RUN pip install --no-cache-dir \
praisonai_tools \
"praisonai>=2.2.31" \
"praisonai>=2.2.34" \
"praisonai[chat]" \
"embedchain[github,youtube]"
+1 -1
View File
@@ -20,7 +20,7 @@ RUN mkdir -p /root/.praison
# Install Python packages (using latest versions)
RUN pip install --no-cache-dir \
praisonai_tools \
"praisonai>=2.2.31" \
"praisonai>=2.2.34" \
"praisonai[ui]" \
"praisonai[chat]" \
"praisonai[realtime]" \
+1 -1
View File
@@ -16,7 +16,7 @@ RUN mkdir -p /root/.praison
# Install Python packages (using latest versions)
RUN pip install --no-cache-dir \
praisonai_tools \
"praisonai>=2.2.31" \
"praisonai>=2.2.34" \
"praisonai[ui]" \
"praisonai[crewai]"
+2 -2
View File
@@ -121,7 +121,7 @@ healthcheck:
## 📦 Package Versions
All Docker images use consistent, up-to-date versions:
- PraisonAI: `>=2.2.31`
- PraisonAI: `>=2.2.34`
- PraisonAI Agents: `>=0.0.92`
- Python: `3.11-slim`
@@ -218,7 +218,7 @@ docker-compose up -d
### Version Pinning
To use specific versions, update the Dockerfile:
```dockerfile
RUN pip install "praisonai==2.2.31" "praisonaiagents==0.0.92"
RUN pip install "praisonai==2.2.34" "praisonaiagents==0.0.92"
```
## 🌐 Production Deployment
@@ -0,0 +1,172 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "29d21289",
"metadata": {
"id": "29d21289"
},
"source": [
"# DeepSeek R1 Qwen3 (8B) - GRPO Agent Demo"
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/DeepSeek_Qwen3_GRPO.ipynb)\n"
],
"metadata": {
"id": "yuOEagMH86WV"
},
"id": "yuOEagMH86WV"
},
{
"cell_type": "markdown",
"id": "0f798657",
"metadata": {
"id": "0f798657"
},
"source": [
"This notebook demonstrates the usage of DeepSeek's Qwen3-8B model with GRPO (Guided Reasoning Prompt Optimization) for interactive conversational reasoning tasks.\n",
"It is designed to simulate a lightweight agent-style reasoning capability in an accessible and interpretable way."
]
},
{
"cell_type": "markdown",
"id": "80f3de9e",
"metadata": {
"id": "80f3de9e"
},
"source": [
"## Dependencies"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "8d1c7f6c",
"metadata": {
"id": "8d1c7f6c"
},
"outputs": [],
"source": [
"!pip install -q transformers accelerate"
]
},
{
"cell_type": "markdown",
"id": "78603e7b",
"metadata": {
"id": "78603e7b"
},
"source": [
"## Tools"
]
},
{
"cell_type": "markdown",
"id": "88e97fbc",
"metadata": {
"id": "88e97fbc"
},
"source": [
"- `transformers`: For model loading and interaction\n",
"- `AutoModelForCausalLM`, `AutoTokenizer`: Interfaces for DeepSeek's LLM"
]
},
{
"cell_type": "markdown",
"id": "37d9bd54",
"metadata": {
"id": "37d9bd54"
},
"source": [
"## YAML Prompt"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "adf5cae5",
"metadata": {
"id": "adf5cae5"
},
"outputs": [],
"source": [
"\n",
"prompt:\n",
" task: \"Reasoning over multi-step instructions\"\n",
" context: \"User provides a math problem or logical question.\"\n",
" model: \"deepseek-ai/deepseek-moe-16b-chat\"\n"
]
},
{
"cell_type": "markdown",
"id": "6985f60c",
"metadata": {
"id": "6985f60c"
},
"source": [
"## Main"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "d74bf686",
"metadata": {
"id": "d74bf686"
},
"outputs": [],
"source": [
"\n",
"from transformers import AutoTokenizer, AutoModelForCausalLM, pipeline\n",
"\n",
"model_id = \"deepseek-ai/deepseek-moe-16b-chat\"\n",
"tokenizer = AutoTokenizer.from_pretrained(model_id)\n",
"model = AutoModelForCausalLM.from_pretrained(model_id, device_map=\"auto\")\n",
"\n",
"pipe = pipeline(\"text-generation\", model=model, tokenizer=tokenizer)\n",
"\n",
"prompt = \"If a train travels 60 miles in 1.5 hours, what is its average speed?\"\n",
"output = pipe(prompt, max_new_tokens=60)[0]['generated_text']\n",
"print(\"🧠 Reasoned Output:\", output)\n"
]
},
{
"cell_type": "markdown",
"id": "c856167f",
"metadata": {
"id": "c856167f"
},
"source": [
"## Output"
]
},
{
"cell_type": "markdown",
"id": "41039ee8",
"metadata": {
"id": "41039ee8"
},
"source": [
"### 🖼️ Output Summary\n",
"\n",
"Prompt: *\"If a train travels 60 miles in 1.5 hours, what is its average speed?\"*\n",
"\n",
"🧠 Output: The model provides a clear reasoning process, such as:\n",
"\n",
"> \"To find the average speed, divide the total distance by total time: 60 / 1.5 = 40 mph.\"\n",
"\n",
"💡 This shows the model's ability to walk through logical steps using GRPO-enhanced reasoning."
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,395 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "127dc323",
"metadata": {
"id": "127dc323"
},
"source": [
"# 📘 KnowledgeAgent - AI-Powered Content Analysis and Summarization Tool"
]
},
{
"cell_type": "markdown",
"id": "8290ecb7",
"metadata": {
"id": "8290ecb7"
},
"source": [
"\n",
"This notebook demonstrates how to create an AI-powered **KnowledgeAgent** using the [PraisonAI](https://github.com/MervinPraison/PraisonAI/) framework. \n",
"The agent performs content analysis and summarization tasks using LLMs and a vector database. \n",
"Runs on Google Colab free tier.\n"
]
},
{
"cell_type": "markdown",
"id": "Lxx3NiCrpFNM",
"metadata": {
"id": "Lxx3NiCrpFNM"
},
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/KnowledgeAgent_PraisonAI.ipynb)\n"
]
},
{
"cell_type": "markdown",
"id": "N4Vxz84co0Ac",
"metadata": {
"id": "N4Vxz84co0Ac"
},
"source": [
"# Dependencies"
]
},
{
"cell_type": "code",
"execution_count": 1,
"id": "1241a155",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "1241a155",
"outputId": "05e987e6-e332-42a6-af0e-109aed2d6016"
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"\u001b[?25l \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m0.0/175.6 kB\u001b[0m \u001b[31m?\u001b[0m eta \u001b[36m-:--:--\u001b[0m\r",
"\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m175.6/175.6 kB\u001b[0m \u001b[31m8.9 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
"\u001b[?25h\u001b[?25l \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m0.0/130.2 kB\u001b[0m \u001b[31m?\u001b[0m eta \u001b[36m-:--:--\u001b[0m\r",
"\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m130.2/130.2 kB\u001b[0m \u001b[31m11.8 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
"\u001b[?25h\u001b[?25l \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m0.0/103.8 kB\u001b[0m \u001b[31m?\u001b[0m eta \u001b[36m-:--:--\u001b[0m\r",
"\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m103.8/103.8 kB\u001b[0m \u001b[31m9.9 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
"\u001b[?25h\u001b[?25l \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m0.0/44.4 kB\u001b[0m \u001b[31m?\u001b[0m eta \u001b[36m-:--:--\u001b[0m\r",
"\u001b[2K \u001b[90m━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━\u001b[0m \u001b[32m44.4/44.4 kB\u001b[0m \u001b[31m3.5 MB/s\u001b[0m eta \u001b[36m0:00:00\u001b[0m\n",
"\u001b[?25h"
]
}
],
"source": [
"!pip install -q praisonaiagents"
]
},
{
"cell_type": "markdown",
"id": "258c378c",
"metadata": {
"id": "258c378c"
},
"source": [
"\n",
"## 🔧 Tools Used\n",
"- [PraisonAI](https://github.com/MervinPraison/PraisonAI): Multi-agent framework for LLMs \n",
"- OpenAI API: Used as the backend model (you'll need an API key) \n",
"- Built-in vector store for document retrieval (RAG) \n"
]
},
{
"cell_type": "markdown",
"id": "26723867",
"metadata": {
"id": "26723867"
},
"source": [
"\n",
"## 🧾 YAML Prompt (Equivalent in Python)\n",
"The agent will:\n",
"- Be called `KnowledgeAgent`\n",
"- Analyze documents or topics\n",
"- Summarize findings in structured format\n"
]
},
{
"cell_type": "markdown",
"id": "vDnilJPOo3Q4",
"metadata": {
"id": "vDnilJPOo3Q4"
},
"source": [
"# Setting Up Your OpenAI API Key"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "7K3qo_5WocdJ",
"metadata": {
"id": "7K3qo_5WocdJ"
},
"outputs": [],
"source": [
"import os\n",
"from getpass import getpass\n",
"\n",
"os.environ[\"OPENAI_API_KEY\"] = getpass(\"Enter your OpenAI API key: your api key here\")"
]
},
{
"cell_type": "markdown",
"id": "8MssHldCpCK4",
"metadata": {
"id": "8MssHldCpCK4"
},
"source": [
"# Main"
]
},
{
"cell_type": "code",
"execution_count": 4,
"id": "55d0c5f1",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 877,
"referenced_widgets": [
"3e9d882fec5947bb86b8aa237e498673",
"8cd0e464954d433b854f6f743e1016ae"
]
},
"id": "55d0c5f1",
"outputId": "795d2f18-edfc-4c53-ac61-c420d0b660d4"
},
"outputs": [
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"><span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">╭─ </span><span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8; font-weight: bold\">Agent Info</span><span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\"> ────────────────────────────────────────────────────────────────────────────────────────────────────╮</span>\n",
"<span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span> <span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span>\n",
"<span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span> <span style=\"color: #ff9b9b; text-decoration-color: #ff9b9b; font-weight: bold\">👤 Agent:</span> <span style=\"color: #ffe5e5; text-decoration-color: #ffe5e5\">KnowledgeAgent</span> <span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span>\n",
"<span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span> <span style=\"color: #b4b4b3; text-decoration-color: #b4b4b3; font-weight: bold\">Role:</span> <span style=\"color: #ffe5e5; text-decoration-color: #ffe5e5\">Assistant</span> <span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span>\n",
"<span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span> <span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">│</span>\n",
"<span style=\"color: #d2e3c8; text-decoration-color: #d2e3c8\">╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯</span>\n",
"</pre>\n"
],
"text/plain": [
"\u001b[38;2;210;227;200m╭─\u001b[0m\u001b[38;2;210;227;200m \u001b[0m\u001b[1;38;2;210;227;200mAgent Info\u001b[0m\u001b[38;2;210;227;200m \u001b[0m\u001b[38;2;210;227;200m───────────────────────────────────────────────────────────────────────────────────────────────────\u001b[0m\u001b[38;2;210;227;200m─╮\u001b[0m\n",
"\u001b[38;2;210;227;200m│\u001b[0m \u001b[38;2;210;227;200m│\u001b[0m\n",
"\u001b[38;2;210;227;200m│\u001b[0m \u001b[1;38;2;255;155;155m👤 Agent:\u001b[0m \u001b[38;2;255;229;229mKnowledgeAgent\u001b[0m \u001b[38;2;210;227;200m│\u001b[0m\n",
"\u001b[38;2;210;227;200m│\u001b[0m \u001b[1;38;2;180;180;179mRole:\u001b[0m \u001b[38;2;255;229;229mAssistant\u001b[0m \u001b[38;2;210;227;200m│\u001b[0m\n",
"\u001b[38;2;210;227;200m│\u001b[0m \u001b[38;2;210;227;200m│\u001b[0m\n",
"\u001b[38;2;210;227;200m╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯\u001b[0m\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "3e9d882fec5947bb86b8aa237e498673",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Output()"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"></pre>\n"
],
"text/plain": []
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\">\n",
"</pre>\n"
],
"text/plain": [
"\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"><span style=\"color: #7f7f7f; text-decoration-color: #7f7f7f\">Response generated in 7.9s</span>\n",
"</pre>\n"
],
"text/plain": [
"\u001b[2mResponse generated in 7.9s\u001b[0m\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"><span style=\"color: #008080; text-decoration-color: #008080\">╭───────────────────────────────────────────────────── Task ──────────────────────────────────────────────────────╮</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> You need to do the following task: Analyze a topic and produce a structured summary. Expected Output: A <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> well-structured paragraph or bullet summary. Please provide only the final result of your work. Do not add any <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> conversation or extra explanation. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯</span>\n",
"</pre>\n"
],
"text/plain": [
"\u001b[36m╭─\u001b[0m\u001b[36m────────────────────────────────────────────────────\u001b[0m\u001b[36m Task \u001b[0m\u001b[36m─────────────────────────────────────────────────────\u001b[0m\u001b[36m─╮\u001b[0m\n",
"\u001b[36m│\u001b[0m You need to do the following task: Analyze a topic and produce a structured summary. Expected Output: A \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m well-structured paragraph or bullet summary. Please provide only the final result of your work. Do not add any \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m conversation or extra explanation. \u001b[36m│\u001b[0m\n",
"\u001b[36m╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯\u001b[0m\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"text/html": [
"<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"><span style=\"color: #008080; text-decoration-color: #008080\">╭─────────────────────────────────────────────────── Response ────────────────────────────────────────────────────╮</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"font-weight: bold\">Topic: The Impact of Artificial Intelligence on Healthcare</span> <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Introduction</span>: Artificial Intelligence (AI) is revolutionizing the healthcare industry by enhancing <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>diagnostic accuracy, personalizing treatment plans, and improving patient outcomes. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Diagnostic Improvements</span>: AI algorithms, particularly in imaging and pathology, can analyze medical data with <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>high precision, leading to early and accurate disease detection, such as in radiology for identifying tumors <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>or in dermatology for skin cancer detection. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Personalized Medicine</span>: AI facilitates the development of personalized treatment plans by analyzing genetic <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>information and predicting patient responses to various treatments, thus optimizing therapeutic efficacy and <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>minimizing adverse effects. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Operational Efficiency</span>: AI streamlines administrative tasks, such as scheduling, patient record management, <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>and billing, reducing the burden on healthcare professionals and allowing them to focus more on patient <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>care. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Predictive Analytics</span>: AI models can predict patient admission rates, potential outbreaks, and disease <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>progression, enabling proactive healthcare management and resource allocation. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Challenges</span>: Despite its benefits, AI in healthcare faces challenges like data privacy concerns, the need for <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>large datasets for training, potential biases in AI algorithms, and the requirement for regulatory <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>frameworks to ensure safety and efficacy. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> • </span><span style=\"font-weight: bold\">Future Prospects</span>: Continued advancements in AI technology promise further integration into healthcare, <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>potentially leading to fully automated diagnostic systems and more sophisticated predictive models, <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">│</span> <span style=\"color: #808000; text-decoration-color: #808000; font-weight: bold\"> </span>ultimately transforming patient care and healthcare delivery. <span style=\"color: #008080; text-decoration-color: #008080\">│</span>\n",
"<span style=\"color: #008080; text-decoration-color: #008080\">╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯</span>\n",
"</pre>\n"
],
"text/plain": [
"\u001b[36m╭─\u001b[0m\u001b[36m──────────────────────────────────────────────────\u001b[0m\u001b[36m Response \u001b[0m\u001b[36m───────────────────────────────────────────────────\u001b[0m\u001b[36m─╮\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1mTopic: The Impact of Artificial Intelligence on Healthcare\u001b[0m \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mIntroduction\u001b[0m: Artificial Intelligence (AI) is revolutionizing the healthcare industry by enhancing \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mdiagnostic accuracy, personalizing treatment plans, and improving patient outcomes. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mDiagnostic Improvements\u001b[0m: AI algorithms, particularly in imaging and pathology, can analyze medical data with \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mhigh precision, leading to early and accurate disease detection, such as in radiology for identifying tumors \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mor in dermatology for skin cancer detection. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mPersonalized Medicine\u001b[0m: AI facilitates the development of personalized treatment plans by analyzing genetic \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0minformation and predicting patient responses to various treatments, thus optimizing therapeutic efficacy and \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mminimizing adverse effects. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mOperational Efficiency\u001b[0m: AI streamlines administrative tasks, such as scheduling, patient record management, \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mand billing, reducing the burden on healthcare professionals and allowing them to focus more on patient \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mcare. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mPredictive Analytics\u001b[0m: AI models can predict patient admission rates, potential outbreaks, and disease \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mprogression, enabling proactive healthcare management and resource allocation. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mChallenges\u001b[0m: Despite its benefits, AI in healthcare faces challenges like data privacy concerns, the need for \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mlarge datasets for training, potential biases in AI algorithms, and the requirement for regulatory \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mframeworks to ensure safety and efficacy. \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m • \u001b[0m\u001b[1mFuture Prospects\u001b[0m: Continued advancements in AI technology promise further integration into healthcare, \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0mpotentially leading to fully automated diagnostic systems and more sophisticated predictive models, \u001b[36m│\u001b[0m\n",
"\u001b[36m│\u001b[0m \u001b[1;33m \u001b[0multimately transforming patient care and healthcare delivery. \u001b[36m│\u001b[0m\n",
"\u001b[36m╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯\u001b[0m\n"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"name": "stdout",
"output_type": "stream",
"text": [
"📄 Output Summary:\n",
"**Topic: The Impact of Artificial Intelligence on Healthcare**\n",
"\n",
"- **Introduction**: Artificial Intelligence (AI) is revolutionizing the healthcare industry by enhancing diagnostic accuracy, personalizing treatment plans, and improving patient outcomes.\n",
" \n",
"- **Diagnostic Improvements**: AI algorithms, particularly in imaging and pathology, can analyze medical data with high precision, leading to early and accurate disease detection, such as in radiology for identifying tumors or in dermatology for skin cancer detection.\n",
"\n",
"- **Personalized Medicine**: AI facilitates the development of personalized treatment plans by analyzing genetic information and predicting patient responses to various treatments, thus optimizing therapeutic efficacy and minimizing adverse effects.\n",
"\n",
"- **Operational Efficiency**: AI streamlines administrative tasks, such as scheduling, patient record management, and billing, reducing the burden on healthcare professionals and allowing them to focus more on patient care.\n",
"\n",
"- **Predictive Analytics**: AI models can predict patient admission rates, potential outbreaks, and disease progression, enabling proactive healthcare management and resource allocation.\n",
"\n",
"- **Challenges**: Despite its benefits, AI in healthcare faces challenges like data privacy concerns, the need for large datasets for training, potential biases in AI algorithms, and the requirement for regulatory frameworks to ensure safety and efficacy.\n",
"\n",
"- **Future Prospects**: Continued advancements in AI technology promise further integration into healthcare, potentially leading to fully automated diagnostic systems and more sophisticated predictive models, ultimately transforming patient care and healthcare delivery.\n"
]
}
],
"source": [
"\n",
"from praisonaiagents import Agent, Task, PraisonAIAgents\n",
"import os\n",
"\n",
"# 🔑 Set your OpenAI API key\n",
"os.environ[\"OPENAI_API_KEY\"] = \"YOUR_API_KEY\"\n",
"# Define agent\n",
"knowledge_agent = Agent(\n",
" name=\"KnowledgeAgent\",\n",
" instructions=\"You are a knowledge expert. Research the given topic and summarize it clearly and concisely.\"\n",
")\n",
"\n",
"# Define task\n",
"knowledge_task = Task(\n",
" name=\"SummarizationTask\",\n",
" description=\"Analyze a topic and produce a structured summary\",\n",
" expected_output=\"A well-structured paragraph or bullet summary\",\n",
" agent=knowledge_agent\n",
")\n",
"\n",
"# Build system\n",
"agents = PraisonAIAgents(\n",
" agents=[knowledge_agent],\n",
" tasks=[knowledge_task],\n",
" process=\"sequential\"\n",
")\n",
"\n",
"# Run the system\n",
"result = agents.start(input=\"Explain how quantum computing differs from classical computing.\")\n",
"print(\"📄 Output Summary:\")\n",
"print(result)\n"
]
},
{
"cell_type": "markdown",
"id": "910d0f04",
"metadata": {
"id": "910d0f04"
},
"source": [
"\n",
"## 📄 Output\n",
"The output will be a structured summary of the input topic (in this case: **quantum vs classical computing**). \n",
"If the model cannot run due to Colab limits, a text description will be printed instead.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
},
"kernelspec": {
"display_name": "Python 3",
"name": "python3"
},
"language_info": {
"name": "python"
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,635 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "7eb3b7a8",
"metadata": {
"id": "7eb3b7a8"
},
"source": [
"# LLaMA3-2 (11B) Vision Model"
]
},
{
"cell_type": "markdown",
"id": "4914e815",
"metadata": {
"id": "4914e815"
},
"source": [
"## Description\n",
"This notebook demonstrates how to use the **LLaMA3-2 (11B) Vision Model** vision-language model for image input and text generation tasks."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/LLaMA3_2_11B_Vision_Model.ipynb)\n"
],
"metadata": {
"id": "j_sehN-6kKcp"
},
"id": "j_sehN-6kKcp"
},
{
"cell_type": "markdown",
"id": "366d7561",
"metadata": {
"id": "366d7561"
},
"source": [
"## Dependencies\n",
"```python\n",
"!pip install transformers accelerate torch torchvision\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "750d4351",
"metadata": {
"id": "750d4351"
},
"source": [
"## Tools\n",
"- 🤗 Transformers\n",
"- PyTorch\n",
"- Vision Model APIs"
]
},
{
"cell_type": "markdown",
"id": "9f053796",
"metadata": {
"id": "9f053796"
},
"source": [
"## YAML Prompt\n",
"```yaml\n",
"mode: vision\n",
"model: LLaMA3-2 (11B) Vision Model\n",
"tasks:\n",
" - image captioning\n",
" - visual question answering\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "b920aca2",
"metadata": {
"id": "b920aca2"
},
"source": [
"## Main\n",
"Below is the simplified main execution to load the model and run basic inference."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "fb97f999",
"metadata": {
"id": "fb97f999"
},
"outputs": [],
"source": [
"%%capture\n",
"import os\n",
"if \"COLAB_\" not in \"\".join(os.environ.keys()):\n",
" !pip install unsloth\n",
"else:\n",
" # Do this only in Colab notebooks! Otherwise use pip install unsloth\n",
" !pip install --no-deps bitsandbytes accelerate xformers==0.0.29.post3 peft trl triton cut_cross_entropy unsloth_zoo\n",
" !pip install sentencepiece protobuf \"datasets>=3.4.1\" huggingface_hub hf_transfer\n",
" !pip install --no-deps unsloth"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "2a6e11d8",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 511,
"referenced_widgets": [
"98d2cd94be9c454f83a18c8bf5fe9aec",
"c6d906d5fa284667a7021b56fb731e98",
"2394d94e0e714ffdb528b55605f40dc0",
"144522321d134e94858678d525a85f80",
"eaa4f5b890c3436bb8da3e74a8eeb237",
"a85bb0dcd185406c885af8d491cf3c22",
"91a165c1dade4c1b9d7c01771b61291e",
"24f8f69538bb469192088f3ffa1ed624",
"f5123643c11240c0bcc3d3588e8e8a1b",
"ef9a483fb2a3478cb94331868ab2db90",
"ce61267651164b50aa49876a05b7296a",
"289cd006e4ff4f018e758890e148c852",
"c8abe988d9864ca1955430b023c223ad",
"ad5361da5e774447b07bab7e0f272813",
"7fd8253214984e578754c1a7f184687e",
"e84d7f0735e045f498a85deee72e4a36",
"0d6664235d744c66bc567215699966b3",
"14ec87fd00454cc9b6e75a37d9cf2c1c",
"79e970816ead4141a8dc3c534db3a54c",
"f90c77c1bd02487da4d91289243c6a28",
"b0ea1c891cd44fb38f874d28f1b71ad7",
"017cce265bf84be7bd9b8ebe5f25047e",
"d0fc6802d6034d33bb33be048799320d",
"21df32143aa4410c885c0b84ce68466a",
"5dc3fb97742846c3bf4e6b99159d88ed",
"16583bf31a1846e0926fcfc3690fa505",
"b3638367ff0749ecabfef81e18c3f3dd",
"c84a668f99be4a74aae5cca75a2448d8",
"8dbb8561b0214721b69a0b4c41a9e431",
"d5bdec8c59af4d3a94ed7d2bfa2b7921",
"2d361e1d14c64f09b3dae11750e287f4",
"1ecf09bddb4046218cc703af721dced3",
"2361b35c79864c10a84b44929f69c547",
"97b945925ec94ee8851187d97a3b3e01",
"b332f446bf5a457bb1bb32862fb25779",
"4408a069a4e341d59423b51c25afbd64",
"f7902776f2a44de294a21f8d9d1f4e73",
"667e586bf81d4f90b17247741fed6a16",
"66b02dd825894df9b4c07fbf6a9d55b7",
"ae9fdc486fee4a07a332d2767aa487d3",
"b237fb86f5b24341a830c3707f881d12",
"8c436fe0faee404e8d61d9afa916d6b3",
"70141c664f464503b8a0821e6fb8aff2",
"03d88b6a463c40febec9e44329493ed3",
"443cae09fcc74bce8c85514c0e3306f8",
"5e3c171ca5494501841b1cabe5c083fe",
"ba6bf08f321841e180630e24ad14e31c",
"c18a21dd2b4f4d53afcf25d5e2f282ba",
"a61ba57420fc4fb387d03fbf2261e0d7",
"fe2444e22fac4ce48a2ac8b9483dd0ab",
"fe43c14445c54ea590a28bc3663d0c48",
"47ade2b90f5d41469fe68aa452043b10",
"3c4722f0972b4bbf995ea7285a61ba26",
"981e19084d2c4c4da0285ab6758e53d0",
"8ae036dfd56e4e92916f2030dbb5d634",
"c90bdb60e0fc46d8aa1d9e858cbbdd07",
"a7e36b913ce946e0808a5bc3f5b9744b",
"1ea701fee9fa4aac92ae9750da494815",
"c85f1cfff87b435f9041ecd4b657587b",
"e4eb768259094b0ea344ac96181842b4",
"51c2efe52566422394209040317384d9",
"c48225673e394ae9873b25a8b13446b9",
"9b97b57c43ec47ffad7e15ab3c7f21be",
"5f810775e57943bdafcceeccca145450",
"b1a430285adc498d836178ba93ec5604",
"43c0b5f1598e487194f846977edb2d9e",
"4f579cd077cd41c798478f572d592f6a",
"56a5f8469b834a998dbf9b195828f3de",
"e21d0116f78140cd9a2dfd548b93cdd9",
"49639c7bec544b3d92340188e9fab090",
"644eb1b7ad734624a51ec0c3435a96dc",
"181c7cd4ce0140b7a7bcdb8bda323529",
"4a9844c83b104b2dbb1b1149e894089b",
"9156991030be4967a32b7014fbb9d202",
"4e5e63413ead4256ad5900667f5c03b2",
"d70e648f960c4f71b0c4b250fef32654",
"ad3adfba64654cf2859f850c3de05e31",
"a37acc4c0f11436c80cb72272709a9fe",
"9b46b99cc8f5432cbce73a2913141033",
"96cc9201587f47679d0262868277b160",
"58691977879e424fa8d480be75a6e70d",
"8edb9a9006df4929b41b6531d9c27c95",
"cbd4cf8895514baa9420289c14455686",
"397e656680024d148a597cad7def07f5",
"c0297069253140978f1ccb5c1fed852c",
"1808e709f81847cabc126abe8552c289",
"f5117b4078194a058dac514abce9d08a",
"ed18219a0316437d8aef630b5de85b75",
"74742a6f4bb94067b6e6703cef8c3941",
"d1abd20ebc684c839df31d06cb5d658f",
"1d3238444dd041839602d3db4ed7fde2",
"daaf3480c1794c8895049dcd8eec3573",
"028dc1c882454b0dbbebdfbeb6eb4ca3",
"28450d6b5cc145afb3f4fda0f133b7ac",
"f5e7b16ff8f84ba888dd1af0e08df12d",
"d7bcadb25ead446181103aaba00f52c0",
"25f52c2d14c54eb09923acf20e85ca07",
"8df67a8cbe0c4734b52754108642ac10",
"04db919ebb474ae6bd1fba3cb9437eb6",
"1a4c9e787979474b9049e36f8c07c12b",
"3de2161fe36a43699a713916adc09857",
"125518e68b4e491a8e6d40c40504a5fb",
"fced4e62adb743798567c2c0f0d90966",
"77c06023e71440308a6aedd86190ab9b",
"2d508731af60413ea81136dc2ab64a76",
"2036bb5ed5fa4bd49e1d76f2b713b6a1",
"f9e6e2e5b59a4a0984ca0a83db0b186d",
"5b0ca7559eea43edb7009bc8ad41dcd6",
"db0696c568d34b6eab55305e2b87c1e2",
"95d28ba0fd2c47e2bb1fc145d82c7164",
"9430d398534341bca671d10e8bc91ddc",
"020c2d09aa4941b5bddfb3ce9470f9e6",
"bf309ecf24bb4ca68f72ce1acf72b739",
"148b83fa058145b98b69e29cda2f9dcc",
"e0ff84feca0f4c52b3c7d23cdff1a110",
"5a5cf37b757f4af78a0ad69f0ed5bfbc",
"65a2889ce3c04085a0702ce3bd75c9c9",
"0f5aee18791e4f8d95f86f6254ac7878",
"6fc02729c4254edcb86daf71336f30d6",
"7f5ece3436c64e51b34c20503d2fc0c3",
"d2c0dc378e864f42bc9994f7bc31ee1d"
]
},
"id": "2a6e11d8",
"outputId": "f63afa9e-e320-4da2-bb91-b7f4f9163379"
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"🦥 Unsloth: Will patch your computer to enable 2x faster free finetuning.\n",
"🦥 Unsloth Zoo will now patch everything to make training faster!\n",
"==((====))== Unsloth 2024.11.9: Fast Mllama vision patching. Transformers = 4.46.2.\n",
" \\\\ /| GPU: Tesla T4. Max memory: 14.748 GB. Platform = Linux.\n",
"O^O/ \\_/ \\ Pytorch: 2.5.1+cu121. CUDA = 7.5. CUDA Toolkit = 12.1.\n",
"\\ / Bfloat16 = FALSE. FA [Xformers = 0.0.28.post3. FA2 = False]\n",
" \"-____-\" Free Apache license: http://github.com/unslothai/unsloth\n",
"Unsloth: Fast downloading is enabled - ignore downloading bars which are red colored!\n"
]
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "98d2cd94be9c454f83a18c8bf5fe9aec",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model.safetensors.index.json: 0%| | 0.00/385k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "289cd006e4ff4f018e758890e148c852",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Downloading shards: 0%| | 0/2 [00:00<?, ?it/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "d0fc6802d6034d33bb33be048799320d",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model-00001-of-00002.safetensors: 0%| | 0.00/5.00G [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "97b945925ec94ee8851187d97a3b3e01",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model-00002-of-00002.safetensors: 0%| | 0.00/2.18G [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "443cae09fcc74bce8c85514c0e3306f8",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Loading checkpoint shards: 0%| | 0/2 [00:00<?, ?it/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "c90bdb60e0fc46d8aa1d9e858cbbdd07",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"generation_config.json: 0%| | 0.00/210 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "4f579cd077cd41c798478f572d592f6a",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"preprocessor_config.json: 0%| | 0.00/477 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "a37acc4c0f11436c80cb72272709a9fe",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer_config.json: 0%| | 0.00/55.9k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "74742a6f4bb94067b6e6703cef8c3941",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer.json: 0%| | 0.00/17.2M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "1a4c9e787979474b9049e36f8c07c12b",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"special_tokens_map.json: 0%| | 0.00/454 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "9430d398534341bca671d10e8bc91ddc",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"chat_template.json: 0%| | 0.00/5.15k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from unsloth import FastVisionModel # FastLanguageModel for LLMs\n",
"import torch\n",
"\n",
"# 4bit pre quantized models we support for 4x faster downloading + no OOMs.\n",
"fourbit_models = [\n",
" \"unsloth/Llama-3.2-11B-Vision-Instruct-bnb-4bit\", # Llama 3.2 vision support\n",
" \"unsloth/Llama-3.2-11B-Vision-bnb-4bit\",\n",
" \"unsloth/Llama-3.2-90B-Vision-Instruct-bnb-4bit\", # Can fit in a 80GB card!\n",
" \"unsloth/Llama-3.2-90B-Vision-bnb-4bit\",\n",
"\n",
" \"unsloth/Pixtral-12B-2409-bnb-4bit\", # Pixtral fits in 16GB!\n",
" \"unsloth/Pixtral-12B-Base-2409-bnb-4bit\", # Pixtral base model\n",
"\n",
" \"unsloth/Qwen2-VL-2B-Instruct-bnb-4bit\", # Qwen2 VL support\n",
" \"unsloth/Qwen2-VL-7B-Instruct-bnb-4bit\",\n",
" \"unsloth/Qwen2-VL-72B-Instruct-bnb-4bit\",\n",
"\n",
" \"unsloth/llava-v1.6-mistral-7b-hf-bnb-4bit\", # Any Llava variant works!\n",
" \"unsloth/llava-1.5-7b-hf-bnb-4bit\",\n",
"] # More models at https://huggingface.co/unsloth\n",
"\n",
"model, tokenizer = FastVisionModel.from_pretrained(\n",
" \"unsloth/Llama-3.2-11B-Vision-Instruct\",\n",
" load_in_4bit = True, # Use 4bit to reduce memory use. False for 16bit LoRA.\n",
" use_gradient_checkpointing = \"unsloth\", # True or \"unsloth\" for long context\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "cbc24d70",
"metadata": {
"id": "cbc24d70"
},
"outputs": [],
"source": [
"model = FastVisionModel.get_peft_model(\n",
" model,\n",
" finetune_vision_layers = True, # False if not finetuning vision layers\n",
" finetune_language_layers = True, # False if not finetuning language layers\n",
" finetune_attention_modules = True, # False if not finetuning attention layers\n",
" finetune_mlp_modules = True, # False if not finetuning MLP layers\n",
"\n",
" r = 16, # The larger, the higher the accuracy, but might overfit\n",
" lora_alpha = 16, # Recommended alpha == r at least\n",
" lora_dropout = 0,\n",
" bias = \"none\",\n",
" random_state = 3407,\n",
" use_rslora = False, # We support rank stabilized LoRA\n",
" loftq_config = None, # And LoftQ\n",
" # target_modules = \"all-linear\", # Optional now! Can specify a list if needed\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "9e47b862",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 177,
"referenced_widgets": [
"aecf49a7a37445dfb4af43fed91cdc97",
"209f0d74e16b4c03a72687d796958863",
"17c372165582427dbc34abfd5dfdaa6c",
"59110c931b0b45d5a61d7dae7c7e7120",
"1ab79420b99e4508944ba5b4361171f8",
"89284068a3be4af4a0d9b8bc50b9afba",
"d11bd8033e4740929088a4fd0ef883c5",
"cc1cf7cbbcae4771be85c3e628510997",
"758e626f5c2f4b0193e1cf27824818ca",
"dfdce9a9549448a8a475db2c2507f5eb",
"4893fac70136425c9aa1c685e4ce71f3",
"ee828b24ee424cfc82b2f3b87636940a",
"115f636f0c0a4c1ebee21d973ff09e40",
"adb8a39222db4fe880c180fe5c601dbe",
"775514e06f1c453fa311d528b3d62749",
"523f128189f746ce9fb7a594e72e9c7e",
"72715b7c03e34b01b5f7715ce658eacd",
"432103db24e448e8b62bce3af49ec581",
"b382f1fd5c1645169079cdef08c14357",
"5ad48ea79bde44639976eeb61377b74d",
"2ae0d6c5c4c1419293e7b3832b8d8a17",
"71f1e8c406a54c52b6983ff2b922be20",
"34c7dbce08a146a7949152b0cac8666d",
"f8e7b74b13864adc9d6cfccaa9a11362",
"2aaa6c22a7d34c2aa20a169236a72f59",
"c79fefc6a20d4bce9eca13b0b1a604aa",
"8463516108b8491d8aaa0449a7f21f05",
"cb71c9d8d57744fb9cfeb740d7ea50e6",
"0241e7fc2a86481389ce140690fc544a",
"315e97f8931941d382ae5b91e1d644a0",
"ebdc57260e224077b0ba08ffbb3fb6a1",
"0ee41ec935844b09850972773468b5de",
"e7fabc6d4ea8476a9459604d745b7f08",
"5034f195628e43b98e4ab33fd297308c",
"46686703d557405685b5e910d81cfb4a",
"55e11fafe31f4147a7a53c870f637527",
"7fa57079e7414449a9b04330c91bd50d",
"add5ec75448b4378b8e7aab92a5e53f5",
"2e2dcbc6ae13435fa6bb91c35dbdf1ae",
"64a4a67880614ecebad79f9ac957d4af",
"dff190bbf4a746d393857037be5e5d72",
"7ebc322bc4824599a6f59ed979eae207",
"d61c2405111d4acc8428e1cebb96c963",
"5263b46f262a40518c43778191394e4a",
"78f33011fc0648439338fb4556284f31",
"b08e04e041a84597b225f2194943d715",
"7d36203af6344d50813eab42af8df957",
"00714fb691c14ca6a9ee14ead204b6c0",
"7d057295875d4525a165c823ff222268",
"be882001119342ebbbbc3f73dbfa5356",
"2713d41644f84b5290c0dd94b2953b2a",
"235bc65f45ac4b369e1e03582b1b2061",
"d2d708ed937b4deb8d72805e98b3aa9b",
"c0fc8d1e49d643b0b9871080545cbb27",
"f9bae803d6944df98773db211a4e98b6"
]
},
"id": "9e47b862",
"outputId": "ac18735b-4865-4634-cdac-0672be9dc0e6"
},
"outputs": [
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "aecf49a7a37445dfb4af43fed91cdc97",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"README.md: 0%| | 0.00/610 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "ee828b24ee424cfc82b2f3b87636940a",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"train-00000-of-00001.parquet: 0%| | 0.00/481M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "34c7dbce08a146a7949152b0cac8666d",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"test-00000-of-00001.parquet: 0%| | 0.00/79.2M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "5034f195628e43b98e4ab33fd297308c",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating train split: 0%| | 0/1978 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "78f33011fc0648439338fb4556284f31",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating test split: 0%| | 0/327 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from datasets import load_dataset\n",
"\n",
"dataset = load_dataset(\"unsloth/Radiology_mini\", split=\"train\")"
]
},
{
"cell_type": "markdown",
"id": "c437c09d",
"metadata": {
"id": "c437c09d"
},
"source": [
"## Output\n",
"This shows a basic output example of the vision-language model."
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,157 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "930bc11c",
"metadata": {
"id": "930bc11c"
},
"source": [
"# Meta Synthetic Data Generator (LLaMA 3.2 - 3B)\n",
"\n",
"This notebook demonstrates how to use Meta's LLaMA 3.2 3B model to generate synthetic data for use in AI training or application prototyping."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Meta_LLaMA3_SyntheticData.ipynb)\n"
],
"metadata": {
"id": "KPi7FpbV9J2d"
},
"id": "KPi7FpbV9J2d"
},
{
"cell_type": "markdown",
"id": "80f68ecf",
"metadata": {
"id": "80f68ecf"
},
"source": [
"## Dependencies"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "7eeb508d",
"metadata": {
"id": "7eeb508d"
},
"outputs": [],
"source": [
"!pip install -q transformers accelerate bitsandbytes"
]
},
{
"cell_type": "markdown",
"id": "eda75a0c",
"metadata": {
"id": "eda75a0c"
},
"source": [
"## Tools\n",
"* `transformers` for model loading and text generation\n",
"* `pipeline` for simplified inference\n",
"* `AutoTokenizer`, `AutoModelForCausalLM` for LLaMA 3.2"
]
},
{
"cell_type": "markdown",
"id": "6ee96383",
"metadata": {
"id": "6ee96383"
},
"source": [
"## YAML Prompt"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "aa4e56ef",
"metadata": {
"id": "aa4e56ef"
},
"outputs": [],
"source": [
"prompt: |\n",
" task: \"Generate a customer complaint email\"\n",
" style: \"Professional\"\n"
]
},
{
"cell_type": "markdown",
"id": "e9fbe400",
"metadata": {
"id": "e9fbe400"
},
"source": [
"## Main"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "3e35336f",
"metadata": {
"id": "3e35336f"
},
"outputs": [],
"source": [
"from transformers import AutoTokenizer, AutoModelForCausalLM, pipeline\n",
"\n",
"# Load tokenizer and model (LLaMA 3.2 - 3B)\n",
"model_id = \"meta-llama/Meta-Llama-3-3B-Instruct\"\n",
"tokenizer = AutoTokenizer.from_pretrained(model_id)\n",
"model = AutoModelForCausalLM.from_pretrained(model_id)\n",
"\n",
"# Create a simple text generation pipeline\n",
"generator = pipeline(\"text-generation\", model=model, tokenizer=tokenizer)\n",
"\n",
"# Example synthetic data prompt\n",
"prompt = \"Create a customer support query about a late delivery.\"\n",
"\n",
"# Generate synthetic text\n",
"output = generator(prompt, max_length=60, do_sample=True)[0]['generated_text']\n",
"print(\"📝 Synthetic Output:\", output)"
]
},
{
"cell_type": "markdown",
"id": "ed28cc2e",
"metadata": {
"id": "ed28cc2e"
},
"source": [
"## Output"
]
},
{
"cell_type": "markdown",
"id": "6fc8f19e",
"metadata": {
"id": "6fc8f19e"
},
"source": [
"🖼️ Output Preview (Text Summary):\n",
"\n",
"Prompt: \"Create a customer support query about a late delivery.\"\n",
"\n",
"📝 Output: The LLaMA model generates a realistic complaint, such as:\n",
"\n",
"\"Dear Support Team, I placed an order two weeks ago and have yet to receive it...\"\n",
"\n",
"🎯 This illustrates how the model can be used to generate realistic synthetic data for tasks like training chatbots or support models.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
File diff suppressed because it is too large. Load diff
@@ -0,0 +1,120 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "468831db",
"metadata": {
"id": "468831db"
},
"source": [
"# Phi-3.5 Mini Conversational Example"
]
},
{
"cell_type": "markdown",
"id": "ecb80fe2",
"metadata": {
"id": "ecb80fe2"
},
"source": [
"**Description:**\n",
"\n",
"Demonstrates lightweight inference using Phi-3.5 Mini, suitable for smaller hardware and educational use cases."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Phi_3_5_Mini_Conversational.ipynb)\n"
],
"metadata": {
"id": "S1erg7-JP6n3"
},
"id": "S1erg7-JP6n3"
},
{
"cell_type": "markdown",
"id": "0822161c",
"metadata": {
"id": "0822161c"
},
"source": [
"**Dependencies**\n",
"\n",
"```python\n",
"!pip install transformers accelerate\n",
"!pip install torch\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "0df5580b",
"metadata": {
"id": "0df5580b"
},
"source": [
"**Tools Used**\n",
"\n",
"- HuggingFace Transformers\n",
"- PyTorch"
]
},
{
"cell_type": "markdown",
"id": "9d6df43d",
"metadata": {
"id": "9d6df43d"
},
"source": [
"**YAML Prompt**\n",
"\n",
"```yaml\n",
"system: You are a helpful assistant.\n",
"user: Explain what an AI model is.\n",
"```"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "0e775593",
"metadata": {
"id": "0e775593"
},
"outputs": [],
"source": [
"from transformers import AutoTokenizer, AutoModelForCausalLM\n",
"\n",
"tokenizer = AutoTokenizer.from_pretrained(\"microsoft/phi-3.5-mini\")\n",
"model = AutoModelForCausalLM.from_pretrained(\"microsoft/phi-3.5-mini\")\n",
"\n",
"inputs = tokenizer(\"What is an AI model?\", return_tensors=\"pt\")\n",
"outputs = model.generate(**inputs, max_new_tokens=40)\n",
"print(tokenizer.decode(outputs[0], skip_special_tokens=True))"
]
},
{
"cell_type": "markdown",
"id": "187fe354",
"metadata": {
"id": "187fe354"
},
"source": [
"**Output**\n",
"\n",
"The model gives a basic explanation of what AI models do.\n",
"\n",
"What is an AI model?\n",
"An AI model is a computer program that is trained on large amounts of data to perform tasks that normally require human intelligence.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,122 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "ddb8fd1c",
"metadata": {
"id": "ddb8fd1c"
},
"source": [
"# Phi-3 Medium Conversational Inference"
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Phi_3_Medium_Conversational.ipynb)\n"
],
"metadata": {
"id": "uMIvNFtYQDKO"
},
"id": "uMIvNFtYQDKO"
},
{
"cell_type": "markdown",
"id": "71a9292d",
"metadata": {
"id": "71a9292d"
},
"source": [
"**Description:**\n",
"\n",
"Run a conversational inference using the Phi-3 Medium model with an efficient pipeline. The notebook illustrates basic loading, prompting, and response generation."
]
},
{
"cell_type": "markdown",
"id": "9023e3f2",
"metadata": {
"id": "9023e3f2"
},
"source": [
"**Dependencies**\n",
"\n",
"```python\n",
"!pip install transformers accelerate\n",
"!pip install torch torchvision\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "8ed8c345",
"metadata": {
"id": "8ed8c345"
},
"source": [
"**Tools Used**\n",
"\n",
"- HuggingFace Transformers\n",
"- Accelerate\n",
"- PyTorch"
]
},
{
"cell_type": "markdown",
"id": "68cb4bd6",
"metadata": {
"id": "68cb4bd6"
},
"source": [
"**YAML Prompt**\n",
"\n",
"```yaml\n",
"system: You are a helpful assistant.\n",
"user: What is the capital of France?\n",
"```"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "be5d0fde",
"metadata": {
"id": "be5d0fde"
},
"outputs": [],
"source": [
"from transformers import AutoTokenizer, AutoModelForCausalLM\n",
"import torch\n",
"\n",
"model = AutoModelForCausalLM.from_pretrained(\"microsoft/phi-3-medium\")\n",
"tokenizer = AutoTokenizer.from_pretrained(\"microsoft/phi-3-medium\")\n",
"\n",
"prompt = \"What is the capital of France?\"\n",
"inputs = tokenizer(prompt, return_tensors=\"pt\")\n",
"outputs = model.generate(**inputs, max_new_tokens=20)\n",
"print(tokenizer.decode(outputs[0], skip_special_tokens=True))"
]
},
{
"cell_type": "markdown",
"id": "4ac8c793",
"metadata": {
"id": "4ac8c793"
},
"source": [
"**Output**\n",
"\n",
"This example shows the model answering a simple geography question.\n",
"\n",
"What is the capital of France? The capital of France is Paris.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
+123
View File
@@ -0,0 +1,123 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "cc1b7810",
"metadata": {
"id": "cc1b7810"
},
"source": [
"# Phi-4 (14B) Conversational with GRPO"
]
},
{
"cell_type": "markdown",
"id": "9c882a2d",
"metadata": {
"id": "9c882a2d"
},
"source": [
"**Description:**\n",
"\n",
"This notebook demonstrates inference using the Phi-4 14B parameter model with GRPO optimization strategy."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Phi_4_14B_GRPO.ipynb)\n"
],
"metadata": {
"id": "Z7azojscP0Ax"
},
"id": "Z7azojscP0Ax"
},
{
"cell_type": "markdown",
"id": "e8616784",
"metadata": {
"id": "e8616784"
},
"source": [
"**Dependencies**\n",
"\n",
"```python\n",
"!pip install transformers accelerate\n",
"!pip install torch\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "09866448",
"metadata": {
"id": "09866448"
},
"source": [
"**Tools Used**\n",
"\n",
"- HuggingFace Transformers\n",
"- GRPO Optimization\n",
"- PyTorch"
]
},
{
"cell_type": "markdown",
"id": "403b0c37",
"metadata": {
"id": "403b0c37"
},
"source": [
"**YAML Prompt**\n",
"\n",
"```yaml\n",
"system: Act as a professional consultant.\n",
"user: How can AI help in healthcare?\n",
"```"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "e1785bcd",
"metadata": {
"id": "e1785bcd"
},
"outputs": [],
"source": [
"from transformers import AutoTokenizer, AutoModelForCausalLM\n",
"\n",
"tokenizer = AutoTokenizer.from_pretrained(\"microsoft/phi-4-14b\")\n",
"model = AutoModelForCausalLM.from_pretrained(\"microsoft/phi-4-14b\")\n",
"\n",
"prompt = \"How can AI help in healthcare?\"\n",
"inputs = tokenizer(prompt, return_tensors=\"pt\")\n",
"outputs = model.generate(**inputs, max_new_tokens=60)\n",
"print(tokenizer.decode(outputs[0], skip_special_tokens=True))"
]
},
{
"cell_type": "markdown",
"id": "074e4e6e",
"metadata": {
"id": "074e4e6e"
},
"source": [
"**Output**\n",
"\n",
"The model generates thoughtful insights on AI applications in healthcare.\n",
"\n",
"How can AI help in healthcare?\n",
"\n",
"AI can assist in healthcare by improving diagnostics, predicting patient outcomes, personalizing treatments, and enhancing administrative workflows. It enables faster data analysis and decision-making, leading to better patient care.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,124 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "7b502c12",
"metadata": {
"id": "7b502c12"
},
"source": [
"# Phi-4 Conversational Chat"
]
},
{
"cell_type": "markdown",
"id": "6f550ca9",
"metadata": {
"id": "6f550ca9"
},
"source": [
"**Description:**\n",
"\n",
"Basic conversational inference with Phi-4 demonstrating chat-style turn-based communication."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Phi_4_Conversational.ipynb)\n"
],
"metadata": {
"id": "CB4mkM7yPmua"
},
"id": "CB4mkM7yPmua"
},
{
"cell_type": "markdown",
"id": "e0db4638",
"metadata": {
"id": "e0db4638"
},
"source": [
"**Dependencies**\n",
"\n",
"```python\n",
"!pip install transformers accelerate\n",
"!pip install torch\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "25ef05dd",
"metadata": {
"id": "25ef05dd"
},
"source": [
"**Tools Used**\n",
"\n",
"- HuggingFace Transformers\n",
"- PyTorch"
]
},
{
"cell_type": "markdown",
"id": "8986b9d8",
"metadata": {
"id": "8986b9d8"
},
"source": [
"**YAML Prompt**\n",
"\n",
"```yaml\n",
"system: You are a tutor.\n",
"user: Teach me what machine learning is.\n",
"```"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "ffdb2319",
"metadata": {
"id": "ffdb2319"
},
"outputs": [],
"source": [
"from transformers import AutoTokenizer, AutoModelForCausalLM\n",
"\n",
"tokenizer = AutoTokenizer.from_pretrained(\"microsoft/phi-4\")\n",
"model = AutoModelForCausalLM.from_pretrained(\"microsoft/phi-4\")\n",
"\n",
"prompt = \"Teach me what machine learning is.\"\n",
"inputs = tokenizer(prompt, return_tensors=\"pt\")\n",
"outputs = model.generate(**inputs, max_new_tokens=80)\n",
"print(tokenizer.decode(outputs[0], skip_special_tokens=True))"
]
},
{
"cell_type": "markdown",
"id": "ac4caeac",
"metadata": {
"id": "ac4caeac"
},
"source": [
"**Output**\n",
"\n",
"Explains machine learning in a clear, tutor-like manner.\n",
"\n",
"Machine learning is a field of artificial intelligence that allows computers to learn from data without being explicitly programmed.\n",
"It involves training algorithms on large datasets so they can recognize patterns, make decisions, or perform tasks.\n",
"There are different types of machine learning, including supervised, unsupervised, and reinforcement learning.\n",
"For example, in supervised learning, a model is trained using labeled data to predict outcomes.\n",
"Overall, machine learning is widely used in applications like recommendation systems, image recognition, and natural language processing.\n"
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,660 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "23d69f99",
"metadata": {
"id": "23d69f99"
},
"source": [
"# Pixtral (12B) Vision Model"
]
},
{
"cell_type": "markdown",
"id": "b842f675",
"metadata": {
"id": "b842f675"
},
"source": [
"## Description\n",
"This notebook demonstrates how to use the **Pixtral (12B) Vision Model** vision-language model for image input and text generation tasks."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Pixtral_12B_Vision_Model.ipynb)\n"
],
"metadata": {
"id": "MilYelUMlD2z"
},
"id": "MilYelUMlD2z"
},
{
"cell_type": "markdown",
"id": "557dba1c",
"metadata": {
"id": "557dba1c"
},
"source": [
"## Dependencies\n",
"```python\n",
"!pip install transformers accelerate torch torchvision\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "2b864df8",
"metadata": {
"id": "2b864df8"
},
"source": [
"## Tools\n",
"- 🤗 Transformers\n",
"- PyTorch\n",
"- Vision Model APIs"
]
},
{
"cell_type": "markdown",
"id": "1b050001",
"metadata": {
"id": "1b050001"
},
"source": [
"## YAML Prompt\n",
"```yaml\n",
"mode: vision\n",
"model: Pixtral (12B) Vision Model\n",
"tasks:\n",
" - image captioning\n",
" - visual question answering\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "44ce2c02",
"metadata": {
"id": "44ce2c02"
},
"source": [
"## Main\n",
"Below is the simplified main execution to load the model and run basic inference."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "c996306e",
"metadata": {
"id": "c996306e"
},
"outputs": [],
"source": [
"%%capture\n",
"import os\n",
"if \"COLAB_\" not in \"\".join(os.environ.keys()):\n",
" !pip install unsloth\n",
"else:\n",
" # Do this only in Colab notebooks! Otherwise use pip install unsloth\n",
" !pip install --no-deps bitsandbytes accelerate xformers==0.0.29.post3 peft trl triton cut_cross_entropy unsloth_zoo\n",
" !pip install sentencepiece protobuf \"datasets>=3.4.1\" huggingface_hub hf_transfer\n",
" !pip install --no-deps unsloth"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "30147f7c",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 543,
"referenced_widgets": [
"8a0ce0af1025429cb3cfcc5b973a4af0",
"6fe6ac6a53f745c5a2736e1b6cb01ff7",
"8d93c4b87f69485e8e97192a8431113f",
"08af812d04fe481fa84e85a6a591c506",
"257fe2a05570417882a606b304087a21",
"6d8e442e771d4955a29a360dee525119",
"00a911ef0d7f4a6d8b1b4f972b0b4d7c",
"766a605b2c5a463d977b8fefb554fea5",
"54ae26be14bc4fb28933af46f45e023a",
"360f3db84aac4728861b74b5a37adcaa",
"a2ae977cf14c461e9fa0cbc5c27e7186",
"d401dcde88274752b4f0786f834527d9",
"5d10ef16c7154f5392519da3ff6a2f0d",
"d8358c67c0b0415098b3e4a4e7ad0cbb",
"4f593d75532d4087bafc02d6ad2b4f79",
"a519350329d04d5096ccb605c9ffd623",
"9cd924df198145ed93d9df07249236cb",
"a01af94f415b4ed18186fa099c3ecbc3",
"27cd2e02e78d4ef8a52ba73a9e214120",
"841f197cba3f455d8fe9a9dafac992d7",
"d6507d692f9743e6b3eed08df94e2a56",
"c3438845441142fa92fec3acd21b3955",
"eb64d7acd375493098e1f7c30e7f2781",
"ad01bece3f444f1382988a65833bebf7",
"281b9b2311e5460aa4df9bbe9f8e22f0",
"34afc68bfe9d4e47ad73b31a34a74b32",
"23c9c94b98f141e8827c37cd26b6138e",
"d2b5a8a0c51c4d04aa1da73a56c2bcd3",
"4587ddab1af04157b8cba09f780ce9b0",
"aab82ec73c0b42fb928fbc74fc44c168",
"45f90f73051b4f898666ecd14f2818f0",
"6f96f236961344418015be410aedc57c",
"6105cefd94bb4a07b9123e461e857c9c",
"d4d3c9f1f54746d8895b66b6d2888ee2",
"eaa7a98acf704791a5c3ca37232c94b9",
"7b1f0430e15a476eb4b59fd5ddb0f9ac",
"481ce6bb0bf74e9592b5a4ef6cbc6d33",
"7a35df90dc40472eb0862deb368da362",
"d4bda244da214ee497b82608944bce6e",
"2cd8ad1cedb0484fa4c5d47b7b25971c",
"68c0b7aee1464e78b1bbd420f540fcf4",
"1fd521ec517348aa9d8dd73757619da4",
"9c967803321d4ca39b663165c2ce1953",
"c39f8980d63a4a5ab17f031e06b03f67",
"b60b17cb67044a82b173f94d781d5174",
"9078d37b65424033b551caf1ae410d2f",
"e5d3e2d9fb7e4f8fbfa84ba66ea0a81c",
"ae50ac57cecb48cb917a2a3ddf3312d0",
"2a85749ab4144e01bb640cd90a1a8697",
"96ce0742a2a247dd84d85ad7b5286f19",
"b67a770e477e40b3a7ca8f4570cb2129",
"79dfa298db314ce2874e86abd8e6b1ba",
"38700d9515ca4ee694010fd7914e0d18",
"7819396bd89b4917beac22678b04b9ec",
"bdbd0b350dbd49e9b463993a3d5c0e92",
"8f1faff5468a46d4a725d095ae31ea3c",
"4a704f4b14614fe6934420a895d9d1a0",
"e67dfbfbba4d4f4298b7ef302830ab40",
"9b6572529f65495693d840718d37e744",
"f06f07a6a1b94dfa9091651c9e95f6f4",
"c3bea8260e5f493d8a470ff98f025324",
"60f44f8bb72645eba40d9320d9d6e447",
"47905056428d4404b73049b3cc437a5a",
"5edec95909a6434ebf0bfd8a60f5887e",
"c9900bd2f3374f858680f5a40efa70a0",
"003f8dc6323b40d29b4f827e14108b20",
"1ef7d525ad2b4a57ae1118a0c3908b1a",
"7630787d9003423c81eac646fb88edc6",
"f41ca30bce18404b953b97548251b556",
"371f6292472d4befb3d8fcfcca290fed",
"4334bb17edbd4b279287ea9723a62a3c",
"b3114bb6194149989d1fa63011299251",
"4827624c03d848bbb473fe94b2d21c22",
"3047608c78ef465199d52959a425c5c0",
"8fb84b1203cb43b5803c11b4a77c0d42",
"426281caaa3f47e393ea8b001123cb22",
"6381166be9444c0a9b98186e978e94cb",
"fe28321b0bf04f58b0d63e7dc617e3ed",
"77335dfe86c34eb08f9085b6b839b8c7",
"49e7c650e0cc4b449ddd2d50f989d541",
"c502fd2bf724410dbcf1528c79f220ce",
"1b8d5199f7144981b5e9ae71f8ea8199",
"2fa87811a24f4b6e9695d7b80817a422",
"25133a67be974e6293bcdb3507529406",
"fdbff4f0bd6b4989b72f8252b5faea16",
"189edd39642b421f879956bea51d853e",
"740ffbd464f041a283b9b2d9396b180c",
"f5661357cbc144c5947529a979360114",
"ec91a47eece543a495f36ed0e051d637",
"443e64f8935544a0b4c159794fd8b272",
"7dd0095387264941a52e8587ebd0fea1",
"363406f847db494f972011724185b02a",
"c21d3532550248b8a927756a510a2770",
"82f03edadab54f949f92dd0c4a60bd55",
"d2488adbea5344329da2b447382139f5",
"fed393eac57747fabee1c2b743828ef8",
"b1d82fdb948b4c5bbee4d327a0f41a21",
"cccdb395613a4256950b7c3d740736fd",
"24c7bdd72f3546c882a7a7c78de5925f",
"db8a5ea365094bc4a87e77d059b4d0d0",
"2f494500c50a42f0ba3589743048cdd8",
"3ec4018cd5e54ba998a0f143f62407cc",
"f3a87c6d2986429cb40979782b38e712",
"4f7fb67e816b44598022407aacf71f19",
"be9935d016a34ac5a272b51261053f13",
"24540fc3ff1944edaa61e6037bec31c8",
"713338a99be84b54877f8e35c953d8ba",
"5586a425c639474ba5d6c0bd6d93328a",
"088d87f186cc4a5d95745d8317cca20e",
"acdecdef8bd14e44bcd36374b944b562",
"1c7c3bfb5ae4472c9bb6e340c012d302",
"41ae4c0601084403ba26a287f485ebeb",
"916e61f972f6439b8135a70100753917",
"36c3f462830247d7a219f1722cae8791",
"69ae06a22fa9488598ed89641cc135b6",
"c5ca864cc0144ddeb72dcbf1f8303609",
"728f786930a14c7a91cb4ff1f97a24ee",
"71704d8853ed40c4a55fa06669393ec9",
"af5c196783e349888eaefc227beadbf0",
"d3aee68f69ad4e5d81a087ec791cc9b1",
"1ec887eb8dac43ba9922e1f9f2111231",
"aa6b598305944d5ab2e2b4afaea8063c",
"a132d68b4ae94f64b80893b9149f7fd8",
"ec8f420a6f7d413bb528a1661aa3a0e8",
"b70265a81e9a49109c18eaad44135562",
"67a1b2e8e39b48849441368c33e16be4",
"e2ec06c317034b5681d83347b530362f",
"97bcd619eea74ed99650a1d8fed1f406",
"14bc6db53fa449049a6a63b422ee54bc",
"70f9cecf2dca4a3badc609b10ffcc8ec",
"cc082399aef94823b67d6e9c33d468e5",
"b4fb273306e941ebaa529e781361acfb"
]
},
"id": "30147f7c",
"outputId": "8b36524b-d22e-43f2-a6e0-cc4209d76736"
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"🦥 Unsloth: Will patch your computer to enable 2x faster free finetuning.\n",
"🦥 Unsloth Zoo will now patch everything to make training faster!\n",
"==((====))== Unsloth 2024.11.9: Fast Pixtral vision patching. Transformers = 4.46.2.\n",
" \\\\ /| GPU: Tesla T4. Max memory: 14.748 GB. Platform = Linux.\n",
"O^O/ \\_/ \\ Pytorch: 2.5.1+cu121. CUDA = 7.5. CUDA Toolkit = 12.1.\n",
"\\ / Bfloat16 = FALSE. FA [Xformers = 0.0.28.post3. FA2 = False]\n",
" \"-____-\" Free Apache license: http://github.com/unslothai/unsloth\n",
"Unsloth: Fast downloading is enabled - ignore downloading bars which are red colored!\n"
]
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "8a0ce0af1025429cb3cfcc5b973a4af0",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model.safetensors.index.json: 0%| | 0.00/316k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "d401dcde88274752b4f0786f834527d9",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Downloading shards: 0%| | 0/2 [00:00<?, ?it/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "eb64d7acd375493098e1f7c30e7f2781",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model-00001-of-00002.safetensors: 0%| | 0.00/4.97G [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "d4d3c9f1f54746d8895b66b6d2888ee2",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model-00002-of-00002.safetensors: 0%| | 0.00/3.57G [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "b60b17cb67044a82b173f94d781d5174",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Loading checkpoint shards: 0%| | 0/2 [00:00<?, ?it/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "8f1faff5468a46d4a725d095ae31ea3c",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"generation_config.json: 0%| | 0.00/133 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "1ef7d525ad2b4a57ae1118a0c3908b1a",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"processor_config.json: 0%| | 0.00/162 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "fe28321b0bf04f58b0d63e7dc617e3ed",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"chat_template.json: 0%| | 0.00/1.59k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "ec91a47eece543a495f36ed0e051d637",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"preprocessor_config.json: 0%| | 0.00/483 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "db8a5ea365094bc4a87e77d059b4d0d0",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer_config.json: 0%| | 0.00/177k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "1c7c3bfb5ae4472c9bb6e340c012d302",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer.json: 0%| | 0.00/17.1M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "aa6b598305944d5ab2e2b4afaea8063c",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"special_tokens_map.json: 0%| | 0.00/552 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from unsloth import FastVisionModel # FastLanguageModel for LLMs\n",
"import torch\n",
"\n",
"# 4bit pre quantized models we support for 4x faster downloading + no OOMs.\n",
"fourbit_models = [\n",
" \"unsloth/Llama-3.2-11B-Vision-Instruct-bnb-4bit\", # Llama 3.2 vision support\n",
" \"unsloth/Llama-3.2-11B-Vision-bnb-4bit\",\n",
" \"unsloth/Llama-3.2-90B-Vision-Instruct-bnb-4bit\", # Can fit in a 80GB card!\n",
" \"unsloth/Llama-3.2-90B-Vision-bnb-4bit\",\n",
"\n",
" \"unsloth/Pixtral-12B-2409-bnb-4bit\", # Pixtral fits in 16GB!\n",
" \"unsloth/Pixtral-12B-Base-2409-bnb-4bit\", # Pixtral base model\n",
"\n",
" \"unsloth/Qwen2-VL-2B-Instruct-bnb-4bit\", # Qwen2 VL support\n",
" \"unsloth/Qwen2-VL-7B-Instruct-bnb-4bit\",\n",
" \"unsloth/Qwen2-VL-72B-Instruct-bnb-4bit\",\n",
"\n",
" \"unsloth/llava-v1.6-mistral-7b-hf-bnb-4bit\", # Any Llava variant works!\n",
" \"unsloth/llava-1.5-7b-hf-bnb-4bit\",\n",
"] # More models at https://huggingface.co/unsloth\n",
"\n",
"model, tokenizer = FastVisionModel.from_pretrained(\n",
" \"unsloth/Pixtral-12B-2409\",\n",
" load_in_4bit = True, # Use 4bit to reduce memory use. False for 16bit LoRA.\n",
" use_gradient_checkpointing = \"unsloth\", # True or \"unsloth\" for long context\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "1c0cd2b0",
"metadata": {
"id": "1c0cd2b0"
},
"outputs": [],
"source": [
"model = FastVisionModel.get_peft_model(\n",
" model,\n",
" # We do NOT finetune vision & attention layers since Pixtral uses more memory!\n",
" finetune_vision_layers = True, # False if not finetuning vision layers\n",
" finetune_language_layers = True, # False if not finetuning language layers\n",
" finetune_attention_modules = False, # False if not finetuning attention layers\n",
" finetune_mlp_modules = True, # False if not finetuning MLP layers\n",
"\n",
" r = 8, # The larger, the higher the accuracy, but might overfit\n",
" lora_alpha = 8, # Recommended alpha == r at least\n",
" lora_dropout = 0,\n",
" bias = \"none\",\n",
" random_state = 3407,\n",
" use_rslora = False, # We support rank stabilized LoRA\n",
" loftq_config = None, # And LoftQ\n",
" # target_modules = \"all-linear\", # Optional now! Can specify a list if needed\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "440fa965",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 177,
"referenced_widgets": [
"453a07e03ee94f528890205d14511da6",
"309ebf7d588244a3ba28d29d56edbc2a",
"dcc1ef7862e240eebefd5985202ef3b2",
"0ef444f87c454640aa657c4c187e94f5",
"d291b920db4b48fb9f3e89bc916db8c8",
"3570f6aec06d461e9259a2bd60c6a16a",
"3ed61e45df71452f844c1f39ea5c9dcf",
"2b6b7fd9d5204198953a0f6fe8333d57",
"e74c5834491b46d5b065665533671407",
"fc9a5b89da594730a09a6bb4c3adb879",
"22b0b4a4585148b2b6f75ecd86ebded3",
"94a24760f2e3453aa615caf5300cd9da",
"52e83aca1e544ffaabc57d149dd0415e",
"b2e5c457d6a246cabcd71459cf2cee8d",
"b8b672b219c347c4a636c1a43f73fda9",
"76e1e2ae0a2944de8eff1c8eea325164",
"6795172d2bb54298ae68cb481cf84822",
"c09587db5ef3473490c1638c359ca945",
"58e75f4e6c3e4ca9a6e6bc6e9865de67",
"0fd6dae874a344678bac899cca709c3b",
"da76163d3abd4ab9b4a7d02efdb15f00",
"dc79ba710e9f4485a6f51d48963c6666",
"9f45d79473ef446ca8f81c08ec82edda",
"c381bddbbb6a4bbd99f90546dfb1867c",
"9ca49f19650848dfbade44d036e166d2",
"348f47ec75d44295b089a0071b747010",
"d7601975774c43e4af927247019c2dab",
"46513f9858a8403b93fc2fb1a0ea8779",
"3d378819a2084a7797e8e8debf9bf815",
"d2080299e24d40cbaecf75aead507415",
"7d64c5f1dac64a49b794e723a5c77620",
"08acfb1a242542d9990577d62118185f",
"6cdfb3c8a1bc45b1ad34dd77feb4d4fe",
"7856e0634b86431382280c591b6f740f",
"cac2e90d5e3449978089a9fe4690cd93",
"01838b1fb6da41e6bee2c632f9873b6e",
"12b8a9e56ff646d4ba7032405183daf3",
"2ef9f2c39bdf4893a4016e0880445e0f",
"d358e59f602245fc96651c018347c448",
"b7aeadfe764542e3ae4dd47e2664e410",
"10523b38a16b4a48b095860653d34a6c",
"ac9cb94447274626afc8580dd17260ad",
"c6bc57fe79f045fabe94281cbe1bd09a",
"05e888e211274b269794cde826c7d1f9",
"6b2c1870e4ae44aba0326535f75c6858",
"c3997e6823fb40349d9c92e32ce28045",
"a4cf715dfb534feb814d426c2cac2b8e",
"f57ddd4b011e428e82a86317d15779aa",
"be6e313fb0b045adb8d8da6702081a0d",
"dc07e208294f47d8b122afc8d415e3c8",
"c2d88ba605ab4c2ab3f9686c5b65b8e8",
"625723d424624ab2ac641b2c369da9e8",
"35f6d9677b67401699e094040eaf8bd2",
"ed9c8e6297654278bb360c13134920cb",
"39d1ac1f430544c087b69e3bdb6ab5d6"
]
},
"id": "440fa965",
"outputId": "54b0ee23-5573-407a-d22f-cda8378461da"
},
"outputs": [
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "453a07e03ee94f528890205d14511da6",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"README.md: 0%| | 0.00/728 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "94a24760f2e3453aa615caf5300cd9da",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"train-00000-of-00001.parquet: 0%| | 0.00/357M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "9f45d79473ef446ca8f81c08ec82edda",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"test-00000-of-00001.parquet: 0%| | 0.00/57.6M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "7856e0634b86431382280c591b6f740f",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating train split: 0%| | 0/8552 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "6b2c1870e4ae44aba0326535f75c6858",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating test split: 0%| | 0/1364 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from datasets import load_dataset\n",
"dataset = load_dataset(\"unsloth/llava-instruct-mix-vsft-mini\", split = \"train\")"
]
},
{
"cell_type": "markdown",
"id": "b9670b46",
"metadata": {
"id": "b9670b46"
},
"source": [
"## Output\n",
"This shows a basic output example of the vision-language model."
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
@@ -0,0 +1,616 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "a627af7f",
"metadata": {
"id": "a627af7f"
},
"source": [
"# Qwen2.5-VL (7B) Vision Model"
]
},
{
"cell_type": "markdown",
"id": "6ca9476a",
"metadata": {
"id": "6ca9476a"
},
"source": [
"## Description\n",
"This notebook demonstrates how to use the **Qwen2.5-VL (7B) Vision Model** vision-language model for image input and text generation tasks."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Qwen2_5_VL_7B_Vision_Model.ipynb)"
],
"metadata": {
"id": "0G9UGDLJk8uV"
},
"id": "0G9UGDLJk8uV"
},
{
"cell_type": "markdown",
"id": "f467ebfe",
"metadata": {
"id": "f467ebfe"
},
"source": [
"## Dependencies\n",
"```python\n",
"!pip install transformers accelerate torch torchvision\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "ea76265d",
"metadata": {
"id": "ea76265d"
},
"source": [
"## Tools\n",
"- 🤗 Transformers\n",
"- PyTorch\n",
"- Vision Model APIs"
]
},
{
"cell_type": "markdown",
"id": "37c57a37",
"metadata": {
"id": "37c57a37"
},
"source": [
"## YAML Prompt\n",
"```yaml\n",
"mode: vision\n",
"model: Qwen2.5-VL (7B) Vision Model\n",
"tasks:\n",
" - image captioning\n",
" - visual question answering\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "7b02bc60",
"metadata": {
"id": "7b02bc60"
},
"source": [
"## Main\n",
"Below is the simplified main execution to load the model and run basic inference."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "6c397c49",
"metadata": {
"id": "6c397c49"
},
"outputs": [],
"source": [
"%%capture\n",
"import os\n",
"if \"COLAB_\" not in \"\".join(os.environ.keys()):\n",
" !pip install unsloth\n",
"else:\n",
" # Do this only in Colab notebooks! Otherwise use pip install unsloth\n",
" !pip install --no-deps bitsandbytes accelerate xformers==0.0.29.post3 peft trl triton cut_cross_entropy unsloth_zoo\n",
" !pip install sentencepiece protobuf \"datasets>=3.4.1\" huggingface_hub hf_transfer\n",
" !pip install --no-deps unsloth"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "18b3d67c",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 513,
"referenced_widgets": [
"73fc3ac47de840cda7a07297153404d5",
"8c8b54f4d34a4b59a5a2513bbc082297",
"7bd2abffca3f4193afffd3f1a7c8ff8a",
"9ecdc7e0e9c247c59e9eab93455153b8",
"84f4e9f7ff6f433bbf13078e43ebbe2a",
"7475f8a404624b1b844d8148fabb493b",
"9d4aae9ebe594bd6875a5963eb6d77ed",
"62b6d78abada429393c499e0479eb56e",
"2aecce21a3a04971b4f5c9fd0b059738",
"2af66136423c41c6908c5a61c6fa2e5d",
"8bf92078d48448848402ede49b1b5182",
"78ae8aea29e04420bcfe616061934d98",
"e22b1706b6be49af8e31d2c512ccaaf6",
"71ac48ba667b4af291df3a33e7643c6c",
"7d16f0e5aaec4429a5b8d3c4878ea74a",
"a21de38381c241309bc798be604c3bf5",
"f26f1de0f3f34010ac0d37d6f3ed74b6",
"0af61827920e415daf64cfcb1685ee63",
"77a82cf2255b43e088812087af4d8ead",
"fad668efab014d28877087f38f3c034e",
"e764888263e54f0ba2f603992d678096",
"2dccbbbdfbf645b8b5896953f6e8a59b",
"45385885a26e42d0b1f52eda382fd6f4",
"ccb21e1b7fc14a6ab10689154ab2b94a",
"f5c7ab8d65c4418a943a51a401720f67",
"f6aaa74bce474abcbc9daf0515b6ffbd",
"76bd63e567e94650a82272ca6fd85011",
"d3cac12f194a40a187bbba68da36173c",
"30439a7bf22f416cbc01cfe87e433e1f",
"3265b3490b11426a8aa44d541981a296",
"78a31b91439c4c99a07f8f8d8dfb548f",
"d2a3a751ac2f491c9e7cb7a4092ab0b6",
"b652bb727c1148c4aac9ed751920e3ae",
"14e519d5e0834fd9a70a111140f8429a",
"41f3770e6d864c1794a1fa93feaf8605",
"6aa1670b808b42db894756b904243947",
"5757f1d68b8f4571a05486d846127b14",
"14cbf1b61170470bbb9d63e31d0ca310",
"3324ce12dc3e45fab9984eb83a92eb39",
"0ccabea3b39d4b148d420e26b53d3990",
"2d65a3b83b524eeaafde8e406e90198f",
"d179ef65b2b842d69548302c2f7a31be",
"2362fd437a134c30b147df947ee97128",
"7f22e31fc7174ff2bfa8bc2624d33dc7",
"643db314d8e94feeb9cd8747909eaabe",
"b80bb8f2cc92400aa34934978f9bc865",
"03f0c63c572249aabb7fb61272af1f1b",
"4113f045f9bc440b8dfaed5dfab14c1b",
"86a231a75d4a4586a53e4c7e74c63550",
"573653d0298246868e5d93069ca0fef5",
"c20a42f12c4545dfafdba22267e44d4b",
"4b74060c0bb44a35b847e6752b93e463",
"7e211233455342d48bd60f6d499b91f5",
"520ca077c6854e6fa1e019c0b209eae7",
"8f1fce549e494998b13f523bd793d300",
"bbb5e6a0a8b64d10802fbf3e89778306",
"0cef8128eeba4638bd268f9a1a364427",
"399cc918cec24db7b99af9e5f3c5adb4",
"3a611a2e00be4da6833172d928802fb9",
"0f2f303ae91349e29132055105fcbdec",
"17c08a96e04244a995e658eeb5a69699",
"9269dee0b0104b22b4043d3661f79350",
"a405cbc6d42d4f8f8be7c05f4e34128c",
"e702e948bb34481d995c75be223c4e16",
"c9949e2b99d14fa0bc4cfc88f42c2afb",
"48bbf9b662af47c5b99ebe24a6b70549",
"c1af10a57c0a40cf818d0974facdcc36",
"e4c1ff933c6e4ef49afbedffcdd99d5c",
"3caf3a6d48da403099bcdee89bda6949",
"7e0bbe2417e0420db1502390ba7c6c2d",
"5522658c84dc47a491f5deb08353b631",
"aecb331a01a44c9e92c74840faaf2616",
"caadc7751ff847b4a831dd6b2b53e60b",
"f0dd55c8f71a4f47a91a7018ab89d092",
"7a2d1ba8441e4a368a505c38d2c811ad",
"6657bbba902e43429224ed9c426389fe",
"a25ba73fb99448a3b46ac3571e2db0be",
"c2f518986b724620bbc67f7b6ede6d96",
"ed214eea73f54928af276883ddd53b5e",
"b241468a1d684fbb820baff6b9f9e362",
"0f7da532813445f1be01977cdec364ab",
"de7ac823a59d488995aa37bfbcec2e5b",
"fc5321766b8742ca97c4a839ba30d421",
"c4256f50e38e481083f3d366bfd91d3f",
"f7e4e90fb3fe4bbb85adb039404dd8e2",
"e0f8b5f130064bd69f4f3298e9536b5a",
"20956dab8f3e4f22830b4d9e56a5232a",
"4efe313f923c4ae585fb8a4353cecd97",
"3af59a3e9ac2430da201262fc54b5998",
"ad746cc40cdb461bba8cf04033d4afc5",
"3d09770f22854ca38213d4a64ace6df3",
"910df16ec7494eb68fb1f8ce95046414",
"080c7eed9cc0475980e85a530c91e616",
"e4fe961d149b461fb1d168d226c8aa1d",
"2a588c12d3814de495fa865a63629ba8",
"607a235508e54fdda0aef75311c7a213",
"383e14f14b0d4328a80e6b0283c421fa",
"913324d3476a4d04887d200f91afc553",
"4c0c6892c4f347deb4a85544664ff1e1",
"a863bb17b5984981bf9bd4ff93e438f4",
"b28286deba7c4152a8d2c21ea0d19402",
"fb9e17975b2349de81115173af6ac17a",
"f3b068de4fa6466e88970b73c868de0a",
"2127bee2928e43578b8b51e3c1fdfabf",
"a97f3d8c7bdf4292ae8ed133f059f635",
"67053bf18cd04347a0f2d2ff6134ae88",
"80e56300aee14b4386832aa1618c5d43",
"d096e33830754ea5b2e8f102548b805a",
"a913ea3370404f5f972754715889aced",
"35db2f7869f44aeab422409d27d5f7ec"
]
},
"id": "18b3d67c",
"outputId": "f0d7f72f-8166-439b-96da-ed7e30f8bdb3"
},
"outputs": [
{
"name": "stdout",
"output_type": "stream",
"text": [
"🦥 Unsloth: Will patch your computer to enable 2x faster free finetuning.\n",
"🦥 Unsloth Zoo will now patch everything to make training faster!\n",
"==((====))== Unsloth 2025.3.19: Fast Qwen2_5_Vl patching. Transformers: 4.50.0.\n",
" \\\\ /| Tesla T4. Num GPUs = 1. Max memory: 14.741 GB. Platform: Linux.\n",
"O^O/ \\_/ \\ Torch: 2.6.0+cu124. CUDA: 7.5. CUDA Toolkit: 12.4. Triton: 3.2.0\n",
"\\ / Bfloat16 = FALSE. FA [Xformers = 0.0.29.post3. FA2 = False]\n",
" \"-____-\" Free license: http://github.com/unslothai/unsloth\n",
"Unsloth: Fast downloading is enabled - ignore downloading bars which are red colored!\n"
]
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "73fc3ac47de840cda7a07297153404d5",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"model.safetensors: 0%| | 0.00/5.97G [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "78ae8aea29e04420bcfe616061934d98",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"generation_config.json: 0%| | 0.00/267 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "45385885a26e42d0b1f52eda382fd6f4",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"preprocessor_config.json: 0%| | 0.00/575 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"name": "stderr",
"output_type": "stream",
"text": [
"Using a slow image processor as `use_fast` is unset and a slow processor was saved with this model. `use_fast=True` will be the default behavior in v4.50, even if the model was saved with a slow processor. This will result in minor differences in outputs. You'll still be able to use a slow processor with `use_fast=False`.\n"
]
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "14e519d5e0834fd9a70a111140f8429a",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer_config.json: 0%| | 0.00/7.33k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "643db314d8e94feeb9cd8747909eaabe",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"vocab.json: 0%| | 0.00/2.78M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "bbb5e6a0a8b64d10802fbf3e89778306",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"merges.txt: 0%| | 0.00/1.67M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "c1af10a57c0a40cf818d0974facdcc36",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"tokenizer.json: 0%| | 0.00/11.4M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "c2f518986b724620bbc67f7b6ede6d96",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"added_tokens.json: 0%| | 0.00/605 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "3af59a3e9ac2430da201262fc54b5998",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"special_tokens_map.json: 0%| | 0.00/614 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "a863bb17b5984981bf9bd4ff93e438f4",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"chat_template.json: 0%| | 0.00/1.05k [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from unsloth import FastVisionModel # FastLanguageModel for LLMs\n",
"import torch\n",
"\n",
"# 4bit pre quantized models we support for 4x faster downloading + no OOMs.\n",
"fourbit_models = [\n",
" \"unsloth/Llama-3.2-11B-Vision-Instruct-bnb-4bit\", # Llama 3.2 vision support\n",
" \"unsloth/Llama-3.2-11B-Vision-bnb-4bit\",\n",
" \"unsloth/Llama-3.2-90B-Vision-Instruct-bnb-4bit\", # Can fit in a 80GB card!\n",
" \"unsloth/Llama-3.2-90B-Vision-bnb-4bit\",\n",
"\n",
" \"unsloth/Pixtral-12B-2409-bnb-4bit\", # Pixtral fits in 16GB!\n",
" \"unsloth/Pixtral-12B-Base-2409-bnb-4bit\", # Pixtral base model\n",
"\n",
" \"unsloth/Qwen2-VL-2B-Instruct-bnb-4bit\", # Qwen2 VL support\n",
" \"unsloth/Qwen2-VL-7B-Instruct-bnb-4bit\",\n",
" \"unsloth/Qwen2-VL-72B-Instruct-bnb-4bit\",\n",
"\n",
" \"unsloth/llava-v1.6-mistral-7b-hf-bnb-4bit\", # Any Llava variant works!\n",
" \"unsloth/llava-1.5-7b-hf-bnb-4bit\",\n",
"] # More models at https://huggingface.co/unsloth\n",
"\n",
"model, tokenizer = FastVisionModel.from_pretrained(\n",
" \"unsloth/Qwen2.5-VL-7B-Instruct-bnb-4bit\",\n",
" load_in_4bit = True, # Use 4bit to reduce memory use. False for 16bit LoRA.\n",
" use_gradient_checkpointing = \"unsloth\", # True or \"unsloth\" for long context\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "45f1a7d8",
"metadata": {
"id": "45f1a7d8"
},
"outputs": [],
"source": [
"model = FastVisionModel.get_peft_model(\n",
" model,\n",
" finetune_vision_layers = True, # False if not finetuning vision layers\n",
" finetune_language_layers = True, # False if not finetuning language layers\n",
" finetune_attention_modules = True, # False if not finetuning attention layers\n",
" finetune_mlp_modules = True, # False if not finetuning MLP layers\n",
"\n",
" r = 16, # The larger, the higher the accuracy, but might overfit\n",
" lora_alpha = 16, # Recommended alpha == r at least\n",
" lora_dropout = 0,\n",
" bias = \"none\",\n",
" random_state = 3407,\n",
" use_rslora = False, # We support rank stabilized LoRA\n",
" loftq_config = None, # And LoftQ\n",
" # target_modules = \"all-linear\", # Optional now! Can specify a list if needed\n",
")"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "915566b6",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 177,
"referenced_widgets": [
"5e4f3f4910d1477b924362c095a0cedd",
"b5a01de096fa4e2daf66e235bd5686bb",
"e9195f3a3e29475f941c302fe2a88a83",
"0d6f6fb66522436786728d8602e2f466",
"94b72e08764c486d8eed43a4557f1d98",
"8e8281a56a3d4879b6b376077890c920",
"630894e18b264f7dae8eddb17304a1cd",
"697fc92abb824cf4a9bc78709640ba54",
"eb6d552d6c1d4e82a521b29b36ae3db0",
"7572f2d06114442ba94fc22761a55346",
"c6dcd15e155949cbb9698e43e55b7a90",
"7365368b63d9425db5d4e5514e6e0586",
"5997909fc34645ce9a03d82ab0932766",
"ea4ebb90b708493c85fa81fecf4d60c0",
"227724312eb045a58616f63c3a5b7407",
"4f58e8a2ddbb4a73a2421ea37c68fea9",
"7e89e5546e394162b7b0f793478527ff",
"db9ea237050045d8861d76bb3b995753",
"3a484309bbe148abb2ef05452850728a",
"5e601d00c0094d999a5b37b9555c111c",
"e7bd6c674af541d08c0acb5e47579156",
"927147d620b0426cb46b49b6d8dc2ffc",
"4ebb36e479884847bcef5736e276dfb9",
"7b5a059a8ef84817851d109fd7e3a7b5",
"0e949ae97d544d65af09cebe63041b8e",
"c817a779a9ff4a848391a7c7dff1e4ca",
"abae462b98c84006b71d4a62c8a47d5a",
"dc1a755aae6c44849d818fd96c046649",
"2650d2ce196e404a98cbfac96d0a9bef",
"36d579fdc2fb4c59b827f5bf7a92abd4",
"fccec1c2a389401eb614f5f1cfb15f0c",
"7b4d303966274c71b50312df12e7b87a",
"ce4bb2dffcf84ae9bf1f8ac86b2d768e",
"639b886f72e24951909e4ffb6cfa247d",
"7b13cf1727a04f5ca6de1f7eb536d800",
"631ce764f4684225a3c1e4455717a555",
"48af93dada914d8b88d5ffffd24ac666",
"4bd339c9d3ee43f39678d2c18baeef53",
"b1b12b8def994e748b08b27abcef4b87",
"bc38022049ce47628d8c215959c38b91",
"331d5d2bc67f44f283fc82481cb60411",
"0a5ad3bd338b4e6ea94a11a199d2f5ba",
"5c41f695158641f485349c20a1405cfd",
"89bc17f1911a43cca7196da232500fd6",
"f5629e8c82c848218f69810e1b21b0e4",
"5244452af0734f3183a7384435f9e1fe",
"69f645decfb64baca11cfbdb9773a458",
"d1788fabe3e34f6eb60fecab3c7490ba",
"8f423066ba8f421495f934a269053cc1",
"569d1435402e4533b0427a4b191b6754",
"b834a7ab12544f9b8305f5728677e921",
"e72ac7c9b7824c81a6e77e6fadad9f9c",
"828ad6e5fcfb44b3b4559ec5682d095d",
"dac611678f4949ae98051bdc975e083f",
"0a21bae13a3c46509db70dbe8e9de5eb"
]
},
"id": "915566b6",
"outputId": "ece64855-55d4-4011-c5b8-33a9bb622734"
},
"outputs": [
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "5e4f3f4910d1477b924362c095a0cedd",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"README.md: 0%| | 0.00/519 [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "7365368b63d9425db5d4e5514e6e0586",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"train-00000-of-00001.parquet: 0%| | 0.00/344M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "4ebb36e479884847bcef5736e276dfb9",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"test-00000-of-00001.parquet: 0%| | 0.00/38.2M [00:00<?, ?B/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "639b886f72e24951909e4ffb6cfa247d",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating train split: 0%| | 0/68686 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
},
{
"data": {
"application/vnd.jupyter.widget-view+json": {
"model_id": "f5629e8c82c848218f69810e1b21b0e4",
"version_major": 2,
"version_minor": 0
},
"text/plain": [
"Generating test split: 0%| | 0/7632 [00:00<?, ? examples/s]"
]
},
"metadata": {},
"output_type": "display_data"
}
],
"source": [
"from datasets import load_dataset\n",
"dataset = load_dataset(\"unsloth/LaTeX_OCR\", split = \"train\")"
]
},
{
"cell_type": "markdown",
"id": "6193435d",
"metadata": {
"id": "6193435d"
},
"source": [
"## Output\n",
"This shows a basic output example of the vision-language model."
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
+146
View File
@@ -0,0 +1,146 @@
{
"cells": [
{
"cell_type": "markdown",
"id": "a050dfc0",
"metadata": {
"id": "a050dfc0"
},
"source": [
"# Sesame CSM (1B) - Text to Speech"
]
},
{
"cell_type": "markdown",
"id": "7c2c61ec",
"metadata": {
"id": "7c2c61ec"
},
"source": [
"This notebook showcases how to generate speech from text using the Sesame CSM 1B model. This is ideal for converting instructional or conversational content into natural audio output."
]
},
{
"cell_type": "markdown",
"source": [
"[![Open in Colab](https://colab.research.google.com/assets/colab-badge.svg)](https://colab.research.google.com/github/DhivyaBharathy-web/PraisonAI/blob/main/examples/cookbooks/Sesame_CSM_1B_TTS.ipynb)\n"
],
"metadata": {
"id": "5SA94wTb9AH-"
},
"id": "5SA94wTb9AH-"
},
{
"cell_type": "markdown",
"id": "ab27fd8d",
"metadata": {
"id": "ab27fd8d"
},
"source": [
"## 🧩 Dependencies"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "ac3a627f",
"metadata": {
"id": "ac3a627f"
},
"outputs": [],
"source": [
"!pip install -q transformers\n",
"!pip install -q torchaudio\n",
"!pip install -q soundfile"
]
},
{
"cell_type": "markdown",
"id": "a382e4d0",
"metadata": {
"id": "a382e4d0"
},
"source": [
"## 🛠️ Tools\n",
"- transformers for loading the model\n",
"- torchaudio for audio processing\n",
"- soundfile for playback"
]
},
{
"cell_type": "markdown",
"id": "7ff6eb6d",
"metadata": {
"id": "7ff6eb6d"
},
"source": [
"## 🧾 YAML Prompt\n",
"```yaml\n",
"task: \"Text to Speech\"\n",
"style: \"Clear, educational\"\n",
"language: \"en\"\n",
"```"
]
},
{
"cell_type": "markdown",
"id": "0ab9cda8",
"metadata": {
"id": "0ab9cda8"
},
"source": [
"## 🧠 Main"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "6459f8bd",
"metadata": {
"id": "6459f8bd"
},
"outputs": [],
"source": [
"from transformers import AutoProcessor, AutoModelForSpeechSeq2Seq\n",
"import torchaudio\n",
"import soundfile as sf\n",
"import torch\n",
"\n",
"processor = AutoProcessor.from_pretrained(\"m-a-p/Sesame-CM\")\n",
"model = AutoModelForSpeechSeq2Seq.from_pretrained(\"m-a-p/Sesame-CM\")\n",
"model = model.to(\"cuda\" if torch.cuda.is_available() else \"cpu\")\n",
"\n",
"text = \"Welcome to the world of voice synthesis using open models!\"\n",
"inputs = processor(text, return_tensors=\"pt\").to(model.device)\n",
"with torch.no_grad():\n",
" outputs = model.generate(**inputs)\n",
"speech = processor.batch_decode(outputs, return_tensors=\"pt\")[0]\n",
"\n",
"sf.write(\"output.wav\", speech.numpy(), 16000)"
]
},
{
"cell_type": "markdown",
"id": "376fe112",
"metadata": {
"id": "376fe112"
},
"source": [
"## 📤 Output\n",
"🖼️ Output Preview (Text Summary):\n",
"\n",
"Prompt: A clear educational text is converted to a .wav file.\n",
"\n",
"🎧 The output audio will say: 'Welcome to the world of voice synthesis using open models!'\n",
"This demonstrates how Sesame-CM can be used for building TTS applications easily."
]
}
],
"metadata": {
"colab": {
"provenance": []
}
},
"nbformat": 4,
"nbformat_minor": 5
}
File diff suppressed because it is too large. Load diff
File diff suppressed because it is too large. Load diff
@@ -269,7 +269,7 @@ async def generate_market_research_report(job_id: str, config: MarketResearchCon
workflow = PraisonAIAgents(
agents=list(agents.values()),
tasks=tasks,
process="workflow",
process="sequential",
verbose=False
)
@@ -296,14 +296,92 @@ async def generate_market_research_report(job_id: str, config: MarketResearchCon
"research_findings": {}
}
# Extract results from each task
if "task_results" in results:
for task_name, result in results["task_results"].items():
if result:
report_data["research_findings"][task_name] = {
"content": result.raw,
"agent": result.agent if hasattr(result, 'agent') else "Unknown"
}
# Extract results from each task with comprehensive logging
print(f"DEBUG: Raw results type: {type(results)}")
print(f"DEBUG: Raw results content: {results}")
if isinstance(results, str):
# Sequential process returns a string result directly
print("DEBUG: Sequential process returned string result")
report_data["research_findings"]["synthesis_report"] = {
"content": results,
"agent": "Research Report Synthesizer",
"section": "Complete Market Research Report"
}
print(f"DEBUG: Added synthesis_report with content length: {len(results)}")
elif isinstance(results, dict):
print(f"DEBUG: Results is dict with keys: {list(results.keys())}")
if "task_results" in results:
print(f"DEBUG: Found task_results: {results['task_results']}")
print(f"DEBUG: task_results type: {type(results['task_results'])}")
for task_name, result in results["task_results"].items():
print(f"DEBUG: Processing task '{task_name}', result type: {type(result)}")
print(f"DEBUG: Result content: {result}")
if result:
# Try multiple ways to extract content
content = None
agent_name = "Unknown"
if hasattr(result, 'raw'):
content = result.raw
print(f"DEBUG: Extracted content from result.raw")
elif hasattr(result, 'content'):
content = result.content
print(f"DEBUG: Extracted content from result.content")
elif isinstance(result, str):
content = result
print(f"DEBUG: Result is string, using directly")
else:
content = str(result)
print(f"DEBUG: Converting result to string")
if hasattr(result, 'agent'):
agent_name = result.agent
elif hasattr(result, 'agent_name'):
agent_name = result.agent_name
if content:
report_data["research_findings"][task_name] = {
"content": content,
"agent": agent_name,
"section": f"Task {task_name}"
}
print(f"DEBUG: Added task '{task_name}' with content length: {len(str(content))}")
else:
print(f"DEBUG: No content found for task '{task_name}'")
else:
print(f"DEBUG: Task '{task_name}' result is None or empty")
else:
print("DEBUG: No 'task_results' found in results dict")
# Try to use the whole results as content
report_data["research_findings"]["workflow_output"] = {
"content": str(results),
"agent": "PraisonAI Workflow",
"section": "Complete Workflow Output"
}
print("DEBUG: Added entire results as workflow_output")
else:
print(f"DEBUG: Unexpected results type: {type(results)}")
report_data["research_findings"]["raw_output"] = {
"content": str(results),
"agent": "Unknown",
"section": "Raw Output"
}
print(f"DEBUG: Final research_findings keys: {list(report_data['research_findings'].keys())}")
print(f"DEBUG: Final research_findings count: {len(report_data['research_findings'])}")
# Generate executive summary from synthesis if available
if "synthesis_report" in report_data["research_findings"]:
content = report_data["research_findings"]["synthesis_report"]["content"]
# Extract first few sentences as executive summary
sentences = content.split('. ')[:3]
report_data["executive_summary"] = '. '.join(sentences) + '.' if sentences else "Market research analysis completed."
print("DEBUG: Generated executive summary from synthesis report")
# Save report to file
report_filename = f"market_research_{job_id}.json"
+170
View File
@@ -0,0 +1,170 @@
# Remote Agent Connectivity
This directory contains examples demonstrating PraisonAI's remote agent connectivity feature, which allows you to connect to agents running on different servers, similar to Google ADK's agent connectivity pattern.
## Overview
The remote agent connectivity feature enables:
- **Direct agent-to-agent connectivity** across networks
- **Session-based communication** with remote agents
- **Google ADK-like API patterns** for familiar usage
- **Automatic connection management** and error handling
## Quick Start
### 1. Start a Remote Agent Server
```bash
# Start a simple remote agent server
python remote_agent_server.py
# Or start multiple agents on one server
python remote_agent_server.py --multiple
```
### 2. Connect from Client
```python
from praisonaiagents import Session
# Connect to remote agent (similar to Google ADK)
session = Session(agent_url="192.168.1.10:8000/agent")
# Send messages to the remote agent
response = session.chat("Hello from the client!")
print(response)
# Alternative method (Google ADK pattern)
response = session.send_message("What can you help me with?")
print(response)
```
## Examples
- **`remote_agent_server.py`** - Set up agents as remote servers
- **`remote_agent_example.py`** - Connect to and communicate with remote agents
## API Comparison
### Google ADK Pattern
```python
from adk.agent import Agent
from adk.session import Session
session = Session(agent_url="192.168.1.10:8000")
response = session.send_message("Hello!")
```
### PraisonAI Pattern
```python
from praisonaiagents import Session
session = Session(agent_url="192.168.1.10:8000/agent")
response = session.chat("Hello!")
# OR
response = session.send_message("Hello!") # Google ADK compatibility
```
## Key Features
### ✅ **Seamless Connectivity**
- Automatic protocol detection (http/https)
- Connection testing and validation
- Configurable timeouts
### ✅ **Error Handling**
- Clear error messages for connection issues
- Graceful handling of network problems
- Appropriate fallbacks for unavailable services
### ✅ **Backward Compatibility**
- Existing local agent functionality unchanged
- Session API works for both local and remote scenarios
- No breaking changes to current code
### ✅ **Flexible Configuration**
- Support for IP:port format (`192.168.1.10:8000`)
- Full URL format (`http://server.com:8000/agent`)
- Customizable endpoints and paths
## Usage Patterns
### Single Remote Agent
```python
# Connect to a specific remote agent
session = Session(agent_url="192.168.1.10:8000/agent")
response = session.chat("Hello from remote client!")
```
### Multiple Remote Agents
```python
# Connect to different specialized agents
research_session = Session(agent_url="192.168.1.10:8000/research")
coding_session = Session(agent_url="192.168.1.10:8000/coding")
research_response = research_session.chat("Find info about AI trends")
coding_response = coding_session.chat("Help me debug this Python code")
```
### Error Handling
```python
try:
session = Session(agent_url="192.168.1.10:8000/agent")
response = session.chat("Test message")
print(f"Response: {response}")
except ConnectionError as e:
print(f"Failed to connect: {e}")
```
## Network Configuration
### Server Setup
```python
# Create and launch agent server
agent = Agent(name="RemoteAgent", role="Assistant")
agent.launch(path="/agent", port=8000, host="0.0.0.0")
```
### Client Connection
```python
# Connect from any network location
session = Session(agent_url="<server-ip>:8000/agent")
```
## Limitations for Remote Sessions
When using remote agent sessions, certain local operations are not available:
- **Memory operations** (`session.memory.*`)
- **Knowledge operations** (`session.knowledge.*`)
- **Local agent creation** (`session.Agent(...)`)
- **State management** (`session.save_state/restore_state`)
This design keeps remote and local operations clearly separated.
## Testing
Run the examples to test the functionality:
```bash
# Terminal 1: Start server
python remote_agent_server.py
# Terminal 2: Test client (update IP as needed)
python remote_agent_example.py
```
## Integration with Existing Code
The remote connectivity feature integrates seamlessly with existing PraisonAI code:
```python
# Existing local code works unchanged
local_session = Session(session_id="local_chat")
local_agent = local_session.Agent(name="LocalAgent", role="Assistant")
# New remote connectivity
remote_session = Session(agent_url="remote-server:8000/agent")
remote_response = remote_session.chat("Hello from remote!")
```
This provides a smooth migration path for applications that need to scale across multiple servers.
@@ -0,0 +1,141 @@
#!/usr/bin/env python3
"""
Remote Agent Connectivity Example
This example demonstrates how to connect to agents running on remote servers,
similar to Google ADK's agent connectivity pattern.
Usage:
1. First, start a remote agent server:
python remote_agent_server.py
2. Then run this client to connect to it:
python remote_agent_example.py
"""
from praisonaiagents import Session
import time
def example_remote_agent_connection():
"""
Example demonstrating remote agent connectivity similar to Google ADK.
"""
print("🌐 Remote Agent Connectivity Example")
print("=" * 50)
# Example 1: Connect to remote agent using IP:port format
try:
print("\n1. Connecting to remote agent at 192.168.1.10:8000...")
# Create a session with remote agent URL (similar to Google ADK)
session = Session(agent_url="192.168.1.10:8000/agent")
print(f"✅ Connected! Session: {session}")
# Send a message to the remote agent
response = session.chat("Hello from the client!")
print(f"📨 Sent: 'Hello from the client!'")
print(f"📨 Received: {response}")
# Send another message using the alias method (Google ADK pattern)
response = session.send_message("What can you help me with?")
print(f"📨 Sent: 'What can you help me with?'")
print(f"📨 Received: {response}")
except ConnectionError as e:
print(f"❌ Connection failed: {e}")
print("💡 Make sure the remote agent server is running at 192.168.1.10:8000")
# Example 2: Connect to localhost for testing
try:
print("\n2. Connecting to localhost for testing...")
# Connect to local server (for testing)
session = Session(agent_url="localhost:8000/agent")
print(f"✅ Connected! Session: {session}")
# Test the connection
response = session.chat("Test message")
print(f"📨 Response: {response}")
except ConnectionError as e:
print(f"❌ Connection failed: {e}")
print("💡 Start a local agent server first with: python remote_agent_server.py")
def example_error_handling():
"""
Example demonstrating error handling for remote sessions.
"""
print("\n\n🚨 Error Handling Examples")
print("=" * 50)
try:
# Create a remote session
session = Session(agent_url="localhost:8000/agent")
# These operations are not available for remote sessions
print("\n❌ Attempting to access memory (should fail)...")
session.memory.store_short_term("test")
except ConnectionError:
print("⚠️ Cannot connect to remote agent (expected if server not running)")
except ValueError as e:
print(f"✅ Correctly caught error: {e}")
try:
session = Session(agent_url="localhost:8000/agent")
print("\n❌ Attempting to create local agent (should fail)...")
agent = session.Agent(name="Test", role="Assistant")
except ConnectionError:
print("⚠️ Cannot connect to remote agent (expected if server not running)")
except ValueError as e:
print(f"✅ Correctly caught error: {e}")
def comparison_with_google_adk():
"""
Shows the comparison between Google ADK and PraisonAI patterns.
"""
print("\n\n🔄 Comparison with Google ADK")
print("=" * 50)
print("\n📋 Google ADK Pattern:")
print("""
from adk.agent import Agent
from adk.session import Session
# Connect to remote agent
session = Session(agent_url="192.168.1.10:8000")
response = session.send_message("Hello from client!")
""")
print("📋 PraisonAI Pattern:")
print("""
from praisonaiagents import Session
# Connect to remote agent
session = Session(agent_url="192.168.1.10:8000/agent")
response = session.chat("Hello from client!")
# OR
response = session.send_message("Hello from client!")
""")
print("✨ Key similarities:")
print("• Direct agent URL connectivity")
print("• Simple session-based API")
print("• Similar message sending patterns")
print("• Error handling for connection issues")
if __name__ == "__main__":
example_remote_agent_connection()
example_error_handling()
comparison_with_google_adk()
print("\n\n🎯 Summary")
print("=" * 50)
print("✅ Remote agent connectivity implemented")
print("✅ Google ADK-like API pattern supported")
print("✅ Backward compatibility maintained")
print("✅ Proper error handling for remote sessions")
print("\n💡 To test with a real server, run remote_agent_server.py first!")
@@ -0,0 +1,103 @@
#!/usr/bin/env python3
"""
Remote Agent Server Example
This example demonstrates how to set up an agent as a remote server
that can be accessed by other clients using the Session(agent_url=...) pattern.
Usage:
python remote_agent_server.py
Then connect from another machine/process:
python remote_agent_example.py
"""
from praisonaiagents import Agent
import time
def setup_remote_agent_server():
"""
Set up an agent as a remote server accessible via HTTP API.
"""
print("🚀 Setting up Remote Agent Server")
print("=" * 50)
# Create an agent that will serve as the remote agent
agent = Agent(
name="RemoteAssistant",
role="Helpful Remote AI Assistant",
goal="Assist users with their queries via remote connections",
backstory="I am an AI assistant running on a remote server, ready to help clients connect and interact with me.",
llm="gpt-4o-mini", # or any other supported model
verbose=True
)
print(f"📝 Created agent: {agent}")
print(f"🔧 Agent details:")
print(f" • Name: {agent.name}")
print(f" • Role: {agent.role}")
print(f" • Goal: {agent.goal}")
# Launch the agent as an HTTP API server
print(f"\n🌐 Launching agent server...")
print(f"📡 Server will be accessible at:")
print(f" • Local: http://localhost:8000/agent")
print(f" • Network: http://<your-ip>:8000/agent")
print(f"\n🔗 Clients can connect using:")
print(f" session = Session(agent_url='<server-ip>:8000/agent')")
print(f"\n⏹️ Press Ctrl+C to stop the server")
print("=" * 50)
# This will start the HTTP server and block until interrupted
try:
agent.launch(path="/agent", port=8000, host="0.0.0.0")
except KeyboardInterrupt:
print("\n\n🛑 Server stopped by user")
except Exception as e:
print(f"\n❌ Server error: {e}")
def setup_multiple_agents():
"""
Example of setting up multiple agents on the same server.
"""
print("🚀 Setting up Multiple Remote Agents")
print("=" * 50)
# Create different specialized agents
research_agent = Agent(
name="ResearchAgent",
role="Research Specialist",
instructions="You are a research specialist who helps with finding and analyzing information."
)
coding_agent = Agent(
name="CodingAgent",
role="Programming Assistant",
instructions="You are a programming assistant who helps with coding questions and debugging."
)
# Launch them on different endpoints
print("🌐 Launching multiple agents:")
print("📡 Research Agent: http://localhost:8000/research")
print("📡 Coding Agent: http://localhost:8000/coding")
print("\n🔗 Connect using:")
print(" research_session = Session(agent_url='localhost:8000/research')")
print(" coding_session = Session(agent_url='localhost:8000/coding')")
try:
# Launch both agents (this will start the server)
research_agent.launch(path="/research", port=8000, host="0.0.0.0")
coding_agent.launch(path="/coding", port=8000, host="0.0.0.0")
except KeyboardInterrupt:
print("\n\n🛑 Server stopped by user")
if __name__ == "__main__":
import sys
if len(sys.argv) > 1 and sys.argv[1] == "--multiple":
setup_multiple_agents()
else:
setup_remote_agent_server()
print("\n\n✅ Remote agent server example completed!")
print("💡 Tip: Use --multiple flag to run multiple agents example")
@@ -368,11 +368,97 @@ class Agent:
max_reflect: int = 3,
min_reflect: int = 1,
reflect_llm: Optional[str] = None,
reflect_prompt: Optional[str] = None,
user_id: Optional[str] = None,
reasoning_steps: bool = False,
guardrail: Optional[Union[Callable[['TaskOutput'], Tuple[bool, Any]], str]] = None,
max_guardrail_retries: int = 3
):
"""Initialize an Agent instance.
Args:
name (Optional[str], optional): Name of the agent used for identification and logging.
If None, defaults to "Agent". Defaults to None.
role (Optional[str], optional): Role or job title that defines the agent's expertise
and behavior patterns. Examples: "Data Analyst", "Content Writer". Defaults to None.
goal (Optional[str], optional): Primary objective or goal the agent aims to achieve.
Defines the agent's purpose and success criteria. Defaults to None.
backstory (Optional[str], optional): Background story or context that shapes the agent's
personality and decision-making approach. Defaults to None.
instructions (Optional[str], optional): Direct instructions that override role, goal,
and backstory when provided. Used for simple, task-specific agents. Defaults to None.
llm (Optional[Union[str, Any]], optional): Language model configuration. Can be a model
name string (e.g., "gpt-4o", "anthropic/claude-3-sonnet") or a configured LLM object.
Defaults to environment variable OPENAI_MODEL_NAME or "gpt-4o".
tools (Optional[List[Any]], optional): List of tools, functions, or capabilities
available to the agent for task execution. Can include callables, tool objects,
or MCP instances. Defaults to None.
function_calling_llm (Optional[Any], optional): Dedicated language model for function
calling operations. If None, uses the main llm parameter. Defaults to None.
max_iter (int, optional): Maximum number of iterations the agent can perform during
task execution to prevent infinite loops. Defaults to 20.
max_rpm (Optional[int], optional): Maximum requests per minute to rate limit API calls
and prevent quota exhaustion. If None, no rate limiting is applied. Defaults to None.
max_execution_time (Optional[int], optional): Maximum execution time in seconds for
agent operations before timeout. If None, no time limit is enforced. Defaults to None.
memory (Optional[Any], optional): Memory system for storing and retrieving information
across conversations. Requires memory dependencies to be installed. Defaults to None.
verbose (bool, optional): Enable detailed logging and status updates during agent
execution for debugging and monitoring. Defaults to True.
allow_delegation (bool, optional): Allow the agent to delegate tasks to other agents
or sub-processes when appropriate. Defaults to False.
step_callback (Optional[Any], optional): Callback function called after each step
of agent execution for custom monitoring or intervention. Defaults to None.
cache (bool, optional): Enable caching of responses and computations to improve
performance and reduce API costs. Defaults to True.
system_template (Optional[str], optional): Custom template for system prompts that
overrides the default system prompt generation. Defaults to None.
prompt_template (Optional[str], optional): Template for formatting user prompts
before sending to the language model. Defaults to None.
response_template (Optional[str], optional): Template for formatting agent responses
before returning to the user. Defaults to None.
allow_code_execution (Optional[bool], optional): Enable the agent to execute code
snippets during task completion. Use with caution for security. Defaults to False.
max_retry_limit (int, optional): Maximum number of retry attempts for failed operations
before giving up. Helps handle transient errors. Defaults to 2.
respect_context_window (bool, optional): Automatically manage context window size
to prevent token limit errors with large conversations. Defaults to True.
code_execution_mode (Literal["safe", "unsafe"], optional): Safety mode for code execution.
"safe" restricts dangerous operations, "unsafe" allows full code execution. Defaults to "safe".
embedder_config (Optional[Dict[str, Any]], optional): Configuration dictionary for
text embedding models used in knowledge retrieval and similarity search. Defaults to None.
knowledge (Optional[List[str]], optional): List of knowledge sources (file paths, URLs,
or text content) to be processed and made available to the agent. Defaults to None.
knowledge_config (Optional[Dict[str, Any]], optional): Configuration for knowledge
processing and retrieval system including chunking and indexing parameters. Defaults to None.
use_system_prompt (Optional[bool], optional): Whether to include system prompts in
conversations to establish agent behavior and context. Defaults to True.
markdown (bool, optional): Enable markdown formatting in agent responses for better
readability and structure. Defaults to True.
self_reflect (bool, optional): Enable self-reflection capabilities where the agent
evaluates and improves its own responses. Defaults to False.
max_reflect (int, optional): Maximum number of self-reflection iterations to prevent
excessive reflection loops. Defaults to 3.
min_reflect (int, optional): Minimum number of self-reflection iterations required
before accepting a response as satisfactory. Defaults to 1.
reflect_llm (Optional[str], optional): Dedicated language model for self-reflection
operations. If None, uses the main llm parameter. Defaults to None.
reflect_prompt (Optional[str], optional): Custom prompt template for self-reflection
that guides the agent's self-evaluation process. Defaults to None.
user_id (Optional[str], optional): Unique identifier for the user or session to
enable personalized responses and memory isolation. Defaults to "praison".
reasoning_steps (bool, optional): Enable step-by-step reasoning output to show the
agent's thought process during problem solving. Defaults to False.
guardrail (Optional[Union[Callable[['TaskOutput'], Tuple[bool, Any]], str]], optional):
Safety mechanism to validate agent outputs. Can be a validation function or
description string for LLM-based validation. Defaults to None.
max_guardrail_retries (int, optional): Maximum number of retry attempts when guardrail
validation fails before giving up. Defaults to 3.
Raises:
ValueError: If all of name, role, goal, backstory, and instructions are None.
ImportError: If memory or LLM features are requested but dependencies are not installed.
"""
# Add check at start if memory is requested
if memory is not None:
try:
@@ -470,6 +556,7 @@ class Agent:
self.markdown = markdown
self.max_reflect = max_reflect
self.min_reflect = min_reflect
self.reflect_prompt = reflect_prompt
# Use the same model selection logic for reflect_llm
self.reflect_llm = reflect_llm or os.getenv('OPENAI_MODEL_NAME', 'gpt-4o')
self.console = Console() # Create a single console instance for the agent
@@ -1230,7 +1317,7 @@ Your Goal: {self.goal}
reflection_prompt = f"""
Reflect on your previous response: '{response_text}'.
Identify any flaws, improvements, or actions.
{self.reflect_prompt if self.reflect_prompt else "Identify any flaws, improvements, or actions."}
Provide a "satisfactory" status ('yes' or 'no').
Output MUST be JSON with 'reflection' and 'satisfactory'.
"""
@@ -1328,7 +1415,7 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
return cleaned
async def achat(self, prompt: str, temperature=0.2, tools=None, output_json=None, output_pydantic=None, reasoning_steps=False):
"""Async version of chat method. TODO: Requires Syncing with chat method."""
"""Async version of chat method with self-reflection support."""
# Log all parameter values when in debug mode
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:
param_info = {
@@ -1501,10 +1588,79 @@ Your Goal: {self.goal}
messages=messages,
temperature=temperature
)
response_text = response.choices[0].message.content
# Handle self-reflection if enabled
if self.self_reflect:
reflection_count = 0
while True:
reflection_prompt = f"""
Reflect on your previous response: '{response_text}'.
{self.reflect_prompt if self.reflect_prompt else "Identify any flaws, improvements, or actions."}
Provide a "satisfactory" status ('yes' or 'no').
Output MUST be JSON with 'reflection' and 'satisfactory'.
"""
# Add reflection prompt to messages
reflection_messages = messages + [
{"role": "assistant", "content": response_text},
{"role": "user", "content": reflection_prompt}
]
try:
reflection_response = await async_client.beta.chat.completions.parse(
model=self.reflect_llm if self.reflect_llm else self.llm,
messages=reflection_messages,
temperature=temperature,
response_format=ReflectionOutput
)
reflection_output = reflection_response.choices[0].message.parsed
if self.verbose:
display_self_reflection(f"Agent {self.name} self reflection (using {self.reflect_llm if self.reflect_llm else self.llm}): reflection='{reflection_output.reflection}' satisfactory='{reflection_output.satisfactory}'", console=self.console)
# Only consider satisfactory after minimum reflections
if reflection_output.satisfactory == "yes" and reflection_count >= self.min_reflect - 1:
if self.verbose:
display_self_reflection("Agent marked the response as satisfactory after meeting minimum reflections", console=self.console)
break
# Check if we've hit max reflections
if reflection_count >= self.max_reflect - 1:
if self.verbose:
display_self_reflection("Maximum reflection count reached, returning current response", console=self.console)
break
# Regenerate response based on reflection
regenerate_messages = reflection_messages + [
{"role": "assistant", "content": f"Self Reflection: {reflection_output.reflection} Satisfactory?: {reflection_output.satisfactory}"},
{"role": "user", "content": "Now regenerate your response using the reflection you made"}
]
new_response = await async_client.chat.completions.create(
model=self.llm,
messages=regenerate_messages,
temperature=temperature
)
response_text = new_response.choices[0].message.content
reflection_count += 1
except Exception as e:
if self.verbose:
display_error(f"Error in parsing self-reflection json {e}. Retrying", console=self.console)
logging.error("Reflection parsing failed.", exc_info=True)
reflection_count += 1
if reflection_count >= self.max_reflect:
break
continue
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:
total_time = time.time() - start_time
logging.debug(f"Agent.achat completed in {total_time:.2f} seconds")
return response.choices[0].message.content
return response_text
except Exception as e:
display_error(f"Error in chat completion: {e}")
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:
+101 -19
View File
@@ -549,6 +549,7 @@ class LLM:
})
should_continue = False
tool_results = [] # Store all tool results
for tool_call in tool_calls:
# Handle both object and dict access patterns
if isinstance(tool_call, dict):
@@ -569,6 +570,7 @@ class LLM:
logging.debug(f"[TOOL_EXEC_DEBUG] About to execute tool {function_name} with args: {arguments}")
tool_result = execute_tool_fn(function_name, arguments)
logging.debug(f"[TOOL_EXEC_DEBUG] Tool execution result: {tool_result}")
tool_results.append(tool_result) # Store the result
if verbose:
display_message = f"Agent {agent_name} called function '{function_name}' with arguments: {arguments}\n"
@@ -601,7 +603,8 @@ class LLM:
# If we reach here, no more tool calls needed - get final response
# Make one more call to get the final summary response
# Special handling for Ollama models that don't automatically process tool results
if self.model and self.model.startswith("ollama/") and tool_result:
ollama_handled = False
if self.model and self.model.startswith("ollama/") and tool_results:
# For Ollama models, we need to explicitly ask the model to process the tool results
# First, check if the response is just a JSON tool call
try:
@@ -614,13 +617,30 @@ class LLM:
# Create a prompt that asks the model to process the tool results based on original context
# Extract the original user query from messages
original_query = ""
for msg in messages:
for msg in reversed(messages): # Look from the end to find the most recent user message
if msg.get("role") == "user":
original_query = msg.get("content", "")
break
content = msg.get("content", "")
# Handle list content (multimodal)
if isinstance(content, list):
for item in content:
if isinstance(item, dict) and item.get("type") == "text":
original_query = item.get("text", "")
break
else:
original_query = content
if original_query:
break
# Create a shorter follow-up prompt
follow_up_prompt = f"Results:\n{json.dumps(tool_result, indent=2)}\nProvide Answer to this Original Question based on the above results: '{original_query}'"
# Create a shorter follow-up prompt with all tool results
# If there's only one result, use it directly; otherwise combine them
if len(tool_results) == 1:
results_text = json.dumps(tool_results[0], indent=2)
else:
results_text = json.dumps(tool_results, indent=2)
follow_up_prompt = f"Results:\n{results_text}\nProvide Answer to this Original Question based on the above results: '{original_query}'"
logging.debug(f"[OLLAMA_DEBUG] Original query extracted: {original_query}")
logging.debug(f"[OLLAMA_DEBUG] Follow-up prompt: {follow_up_prompt[:200]}...")
# Make a follow-up call to process the results
follow_up_messages = [
@@ -653,12 +673,33 @@ class LLM:
):
if chunk and chunk.choices and chunk.choices[0].delta.content:
response_text += chunk.choices[0].delta.content
# Set flag to indicate Ollama was handled
ollama_handled = True
final_response_text = response_text.strip()
logging.debug(f"[OLLAMA_DEBUG] Ollama follow-up response: {final_response_text[:200]}...")
# Display the response if we got one
if final_response_text and verbose:
display_interaction(
original_prompt,
final_response_text,
markdown=markdown,
generation_time=time.time() - start_time,
console=console
)
# Return the final response after processing Ollama's follow-up
if final_response_text:
return final_response_text
else:
logging.warning("[OLLAMA_DEBUG] Ollama follow-up returned empty response")
except (json.JSONDecodeError, KeyError):
# Not a JSON response or not a tool call format, continue normally
pass
# If reasoning_steps is True, do a single non-streaming call
elif reasoning_steps:
# If reasoning_steps is True and we haven't handled Ollama already, do a single non-streaming call
if reasoning_steps and not ollama_handled:
resp = litellm.completion(
**self._build_completion_params(
messages=messages,
@@ -688,8 +729,8 @@ class LLM:
console=console
)
# Otherwise do the existing streaming approach
else:
# Otherwise do the existing streaming approach if not already handled
elif not ollama_handled:
# Get response after tool calls with streaming
if verbose:
with Live(display_generating("", current_time), console=console, refresh_per_second=4) as live:
@@ -1225,6 +1266,7 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
"tool_calls": serializable_tool_calls
})
tool_results = [] # Store all tool results
for tool_call in tool_calls:
# Handle both object and dict access patterns
if isinstance(tool_call, dict):
@@ -1243,6 +1285,7 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
tool_call_id = f"tool_{id(tool_call)}"
tool_result = await execute_tool_fn(function_name, arguments)
tool_results.append(tool_result) # Store the result
if verbose:
display_message = f"Agent {agent_name} called function '{function_name}' with arguments: {arguments}\n"
@@ -1261,7 +1304,8 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
response_text = ""
# Special handling for Ollama models that don't automatically process tool results
if self._is_ollama_provider() and tool_result:
ollama_handled = False
if self._is_ollama_provider() and tool_results:
# For Ollama models, we need to explicitly ask the model to process the tool results
# First, check if the response is just a JSON tool call
try:
@@ -1274,13 +1318,30 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
# Create a prompt that asks the model to process the tool results based on original context
# Extract the original user query from messages
original_query = ""
for msg in messages:
for msg in reversed(messages): # Look from the end to find the most recent user message
if msg.get("role") == "user":
original_query = msg.get("content", "")
break
content = msg.get("content", "")
# Handle list content (multimodal)
if isinstance(content, list):
for item in content:
if isinstance(item, dict) and item.get("type") == "text":
original_query = item.get("text", "")
break
else:
original_query = content
if original_query:
break
# Create a shorter follow-up prompt
follow_up_prompt = f"Results:\n{json.dumps(tool_result, indent=2)}\nProvide Answer to this Original Question based on the above results: '{original_query}'"
# Create a shorter follow-up prompt with all tool results
# If there's only one result, use it directly; otherwise combine them
if len(tool_results) == 1:
results_text = json.dumps(tool_results[0], indent=2)
else:
results_text = json.dumps(tool_results, indent=2)
follow_up_prompt = f"Results:\n{results_text}\nProvide Answer to this Original Question based on the above results: '{original_query}'"
logging.debug(f"[OLLAMA_DEBUG] Original query extracted: {original_query}")
logging.debug(f"[OLLAMA_DEBUG] Follow-up prompt: {follow_up_prompt[:200]}...")
# Make a follow-up call to process the results
follow_up_messages = [
@@ -1313,12 +1374,33 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
):
if chunk and chunk.choices and chunk.choices[0].delta.content:
response_text += chunk.choices[0].delta.content
# Set flag to indicate Ollama was handled
ollama_handled = True
final_response_text = response_text.strip()
logging.debug(f"[OLLAMA_DEBUG] Ollama follow-up response: {final_response_text[:200]}...")
# Display the response if we got one
if final_response_text and verbose:
display_interaction(
original_prompt,
final_response_text,
markdown=markdown,
generation_time=time.time() - start_time,
console=console
)
# Return the final response after processing Ollama's follow-up
if final_response_text:
return final_response_text
else:
logging.warning("[OLLAMA_DEBUG] Ollama follow-up returned empty response")
except (json.JSONDecodeError, KeyError):
# Not a JSON response or not a tool call format, continue normally
pass
# If no special handling was needed or if it's not an Ollama model
elif reasoning_steps:
if reasoning_steps and not ollama_handled:
# Non-streaming call to capture reasoning
resp = await litellm.acompletion(
**self._build_completion_params(
@@ -1348,8 +1430,8 @@ Output MUST be JSON with 'reflection' and 'satisfactory'.
generation_time=time.time() - start_time,
console=console
)
else:
# Get response after tool calls with streaming
elif not ollama_handled:
# Get response after tool calls with streaming if not already handled
if verbose:
async for chunk in await litellm.acompletion(
**self._build_completion_params(
+172 -31
View File
@@ -7,6 +7,9 @@ session API for developers building stateful agent applications.
import os
import uuid
import requests
import json
import time
from typing import Any, Dict, List, Optional
from .agent import Agent
from .memory import Memory
@@ -22,68 +25,90 @@ class Session:
- Memory operations (short-term, long-term, user-specific)
- Knowledge base operations
- Agent state management
- Remote agent connectivity
Example:
Examples:
# Local session with agent
session = Session(session_id="chat_123", user_id="user_456")
agent = session.Agent(name="Assistant", role="Helpful AI")
# Create stateful agent
agent = session.Agent(
name="Assistant",
role="Helpful AI",
memory=True
)
# Remote agent session (similar to Google ADK)
session = Session(agent_url="192.168.1.10:8000/agent")
response = session.chat("Hello from remote client!")
# Save session state
session.save_state({"conversation_topic": "AI research"})
# Restore state later
session.restore_state()
"""
def __init__(
self,
session_id: Optional[str] = None,
user_id: Optional[str] = None,
agent_url: Optional[str] = None,
memory_config: Optional[Dict[str, Any]] = None,
knowledge_config: Optional[Dict[str, Any]] = None
knowledge_config: Optional[Dict[str, Any]] = None,
timeout: int = 30
):
"""
Initialize a new session with optional persistence.
Initialize a new session with optional persistence or remote agent connectivity.
Args:
session_id: Unique session identifier. Auto-generated if None.
user_id: User identifier for user-specific memory operations.
agent_url: URL of remote agent for direct connectivity (e.g., "192.168.1.10:8000/agent")
memory_config: Configuration for memory system (defaults to RAG)
knowledge_config: Configuration for knowledge base system
knowledge_config: Configuration for knowledge base system
timeout: HTTP timeout for remote agent calls (default: 30 seconds)
"""
self.session_id = session_id or str(uuid.uuid4())[:8]
self.user_id = user_id or "default_user"
self.agent_url = agent_url
self.timeout = timeout
self.is_remote = agent_url is not None
# Initialize memory with sensible defaults
default_memory_config = {
"provider": "rag",
"use_embedding": True,
"rag_db_path": f".praison/sessions/{self.session_id}/chroma_db"
}
if memory_config:
default_memory_config.update(memory_config)
self.memory_config = default_memory_config
# Validate agent_url format
if self.is_remote:
if not self.agent_url.startswith(('http://', 'https://')):
# Assume http if no protocol specified
self.agent_url = f"http://{self.agent_url}"
# Test connectivity to remote agent
self._test_remote_connection()
# Initialize knowledge with session-specific config
default_knowledge_config = knowledge_config or {}
self.knowledge_config = default_knowledge_config
# Initialize memory with sensible defaults (only for local sessions)
if not self.is_remote:
default_memory_config = {
"provider": "rag",
"use_embedding": True,
"rag_db_path": f".praison/sessions/{self.session_id}/chroma_db"
}
if memory_config:
default_memory_config.update(memory_config)
self.memory_config = default_memory_config
# Create session directory
os.makedirs(f".praison/sessions/{self.session_id}", exist_ok=True)
# Initialize knowledge with session-specific config
default_knowledge_config = knowledge_config or {}
self.knowledge_config = default_knowledge_config
# Initialize components lazily
self._memory = None
self._knowledge = None
self._agents_instance = None
# Create session directory
os.makedirs(f".praison/sessions/{self.session_id}", exist_ok=True)
# Initialize components lazily
self._memory = None
self._knowledge = None
self._agents_instance = None
else:
# For remote sessions, disable local memory/knowledge
self.memory_config = {}
self.knowledge_config = {}
self._memory = None
self._knowledge = None
self._agents_instance = None
@property
def memory(self) -> Memory:
"""Lazy-loaded memory instance"""
if self.is_remote:
raise ValueError("Memory operations are not available for remote agent sessions")
if self._memory is None:
self._memory = Memory(config=self.memory_config)
return self._memory
@@ -91,6 +116,8 @@ class Session:
@property
def knowledge(self) -> Knowledge:
"""Lazy-loaded knowledge instance"""
if self.is_remote:
raise ValueError("Knowledge operations are not available for remote agent sessions")
if self._knowledge is None:
self._knowledge = Knowledge(config=self.knowledge_config)
return self._knowledge
@@ -119,7 +146,13 @@ class Session:
Returns:
Configured Agent instance
Raises:
ValueError: If this is a remote session (use chat() instead)
"""
if self.is_remote:
raise ValueError("Cannot create local agents in remote sessions. Use chat() to communicate with the remote agent.")
agent_kwargs = {
"name": name,
"role": role,
@@ -150,7 +183,12 @@ class Session:
Args:
state_data: Dictionary of state data to save
Raises:
ValueError: If this is a remote session
"""
if self.is_remote:
raise ValueError("State operations are not available for remote agent sessions")
state_text = f"Session state: {state_data}"
self.memory.store_short_term(
text=state_text,
@@ -168,7 +206,12 @@ class Session:
Returns:
Dictionary of restored state data
Raises:
ValueError: If this is a remote session
"""
if self.is_remote:
raise ValueError("State operations are not available for remote agent sessions")
# Use metadata-based search for better SQLite compatibility
results = self.memory.search_short_term(
query=f"type:session_state",
@@ -284,7 +327,105 @@ class Session:
max_items=max_items
)
def _test_remote_connection(self) -> None:
"""
Test connectivity to the remote agent.
Raises:
ConnectionError: If unable to connect to the remote agent
"""
try:
# Try a simple GET request to check if the server is responding
test_url = self.agent_url.rstrip('/') + '/health' if '/health' not in self.agent_url else self.agent_url
response = requests.get(test_url, timeout=self.timeout)
if response.status_code != 200:
# If health endpoint fails, try the main endpoint
response = requests.head(self.agent_url, timeout=self.timeout)
if response.status_code not in [200, 405]: # 405 = Method Not Allowed is OK
raise ConnectionError(f"Remote agent returned status code: {response.status_code}")
print(f"✅ Successfully connected to remote agent at {self.agent_url}")
except requests.exceptions.Timeout:
raise ConnectionError(f"Timeout connecting to remote agent at {self.agent_url}")
except requests.exceptions.ConnectionError:
raise ConnectionError(f"Failed to connect to remote agent at {self.agent_url}")
except Exception as e:
raise ConnectionError(f"Error connecting to remote agent: {str(e)}")
def chat(self, message: str, **kwargs) -> str:
"""
Send a message to the remote agent or handle local session.
Args:
message: The message to send to the agent
**kwargs: Additional parameters for the request
Returns:
The agent's response
Raises:
ValueError: If this is not a remote session
ConnectionError: If unable to communicate with remote agent
"""
if not self.is_remote:
raise ValueError("chat() method is only available for remote agent sessions. Use Agent.chat() for local agents.")
try:
# Prepare the request payload
payload = {
"query": message,
"session_id": self.session_id,
"user_id": self.user_id,
**kwargs
}
# Send POST request to the remote agent
response = requests.post(
self.agent_url,
json=payload,
headers={"Content-Type": "application/json"},
timeout=self.timeout
)
# Check if request was successful
response.raise_for_status()
# Parse the response
result = response.json()
# Extract the agent's response
if isinstance(result, dict):
return result.get("response", str(result))
else:
return str(result)
except requests.exceptions.Timeout:
raise ConnectionError(f"Timeout communicating with remote agent at {self.agent_url}")
except requests.exceptions.ConnectionError:
raise ConnectionError(f"Failed to communicate with remote agent at {self.agent_url}")
except requests.exceptions.HTTPError as e:
raise ConnectionError(f"HTTP error from remote agent: {e}")
except json.JSONDecodeError:
# If response is not JSON, return the raw text
return response.text
except Exception as e:
raise ConnectionError(f"Error communicating with remote agent: {str(e)}")
def send_message(self, message: str, **kwargs) -> str:
"""
Alias for chat() method to match Google ADK pattern.
Args:
message: The message to send to the agent
**kwargs: Additional parameters for the request
Returns:
The agent's response
"""
return self.chat(message, **kwargs)
def __str__(self) -> str:
if self.is_remote:
return f"Session(id='{self.session_id}', user='{self.user_id}', remote_agent='{self.agent_url}')"
return f"Session(id='{self.session_id}', user='{self.user_id}')"
def __repr__(self) -> str:
@@ -86,7 +86,9 @@ class MinimalTelemetry:
self._posthog = Posthog(
project_api_key='phc_skZpl3eFLQJ4iYjsERNMbCO6jfeSJi2vyZlPahKgxZ7',
host='https://eu.i.posthog.com',
disable_geoip=True
disable_geoip=True,
on_error=lambda e: self.logger.debug(f"PostHog error: {e}"),
sync_mode=False # Use async mode to prevent blocking
)
except:
self._posthog = None
@@ -220,6 +222,7 @@ class MinimalTelemetry:
'$geoip_disable': True
}
)
# Don't flush here - let PostHog handle it asynchronously
except:
pass
@@ -227,6 +230,25 @@ class MinimalTelemetry:
for key in self._metrics:
if isinstance(self._metrics[key], int):
self._metrics[key] = 0
def shutdown(self):
"""
Shutdown telemetry and ensure all events are sent.
"""
if not self.enabled:
return
# Final flush
self.flush()
# Shutdown PostHog if available
if hasattr(self, '_posthog') and self._posthog:
try:
# Force a synchronous flush before shutdown
self._posthog.flush()
self._posthog.shutdown()
except:
pass
# Global telemetry instance
+1 -1
View File
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
[project]
name = "praisonaiagents"
version = "0.0.104"
version = "0.0.107"
description = "Praison AI agents for completing complex tasks with Self Reflection Agents"
requires-python = ">=3.10"
authors = [
+1
View File
@@ -2,6 +2,7 @@
pydantic
rich
openai>=1.30.0
posthog>=3.0.0
# Memory dependencies
chromadb>=0.5.23
+28 -25
View File
@@ -1,33 +1,36 @@
from praisonaiagents import Agent, Task, PraisonAIAgents
import os
from dotenv import load_dotenv
load_dotenv()
llm_config = {
"model": "openai/gpt-4o-mini",
"api_key": os.getenv('OPENAI_API_KEY'),
"temperature": 0.7,
"max_tokens": 2000
}
blog_agent = Agent(
role="Blog Writer",
goal="Write a blog post about AI",
backstory="Expert at writing blog posts",
llm=llm_config,
from praisonaiagents.tools import (
read_file, write_file, list_files, get_file_info,
copy_file, move_file, delete_file
)
blog_task = Task(
description="Write a blog post about AI trends in 1 paragraph",
expected_output="Well-written blog post about AI trends",
agent=blog_agent
# Get user input
d = input("Demande: ")
# Create file manager agent
file_manager_agent = Agent(
name="FileManager",
tools=[read_file, write_file, list_files, get_file_info,
copy_file, move_file, delete_file],
llm={
"model": "ollama/llama3.2",
"base_url": "http://localhost:11434" # Ollama default
}
)
# Dynamically create a task based on input
file_task = Task(
name="Q",
description=f"faire '{d}'.",
expected_output=f"'{d}' bien fait.",
agent=file_manager_agent
)
# Run agent with the task
agents = PraisonAIAgents(
agents=[blog_agent],
tasks=[blog_task],
memory=False
agents=[file_manager_agent],
tasks=[file_task],
process="sequential"
)
result = agents.start()
agents.start()
@@ -0,0 +1,161 @@
#!/usr/bin/env python3
"""
Test script to verify Ollama empty response fix for both sync and async methods.
"""
import asyncio
import logging
from praisonaiagents import Agent, Task, PraisonAIAgents, TaskOutput
from typing import Dict, Any
# Enable debug logging
logging.basicConfig(level=logging.DEBUG)
# Define a simple tool for testing
def search_tool(query: str) -> Dict[str, Any]:
"""Simulate a search tool that returns results."""
logging.debug(f"[TEST] Search tool called with query: {query}")
results = {
"results": [
{"title": "Result 1", "description": f"Information about {query}"},
{"title": "Result 2", "description": f"More details on {query}"}
],
"total": 2
}
logging.debug(f"[TEST] Search tool returning: {results}")
return results
# Test with both sync and async workflows
async def test_model_async(model_name: str):
print(f"\n{'='*60}")
print(f"Testing ASYNC with model: {model_name}")
print('='*60)
# Create agent with the search tool
agent = Agent(
name="SearchAgent",
role="Information Researcher",
goal="Search for information and provide helpful answers",
backstory="You are an expert at finding and summarizing information.",
llm=model_name,
tools=[search_tool],
verbose=True
)
# Create a task that requires tool usage
task = Task(
name="search_task",
description="Search for information about 'Python programming' and provide a summary of what you found.",
expected_output="A clear summary of the search results",
agent=agent
)
# Create and run the workflow
workflow = PraisonAIAgents(
agents=[agent],
tasks=[task],
verbose=True
)
try:
result = await workflow.astart() # Use async start
print(f"\n{'='*60}")
print(f"ASYNC RESULT for {model_name}:")
print('='*60)
print(result)
# Check if result is empty
if not result or (isinstance(result, dict) and not result.get('task_results', {}).get('search_task', {}).get('output')):
print(f"\n❌ ERROR: Empty response from {model_name} (async)")
return False
else:
print(f"\n✅ SUCCESS: Got valid response from {model_name} (async)")
return True
except Exception as e:
print(f"\n❌ ERROR with {model_name} (async): {e}")
import traceback
traceback.print_exc()
return False
def test_model_sync(model_name: str):
print(f"\n{'='*60}")
print(f"Testing SYNC with model: {model_name}")
print('='*60)
# Create agent with the search tool
agent = Agent(
name="SearchAgent",
role="Information Researcher",
goal="Search for information and provide helpful answers",
backstory="You are an expert at finding and summarizing information.",
llm=model_name,
tools=[search_tool],
verbose=True
)
# Create a task that requires tool usage
task = Task(
name="search_task",
description="Search for information about 'Python programming' and provide a summary of what you found.",
expected_output="A clear summary of the search results",
agent=agent
)
# Create and run the workflow
workflow = PraisonAIAgents(
agents=[agent],
tasks=[task],
verbose=True
)
try:
result = workflow.start() # Use sync start
print(f"\n{'='*60}")
print(f"SYNC RESULT for {model_name}:")
print('='*60)
print(result)
# Check if result is empty
if not result or (isinstance(result, dict) and not result.get('task_results', {}).get('search_task', {}).get('output')):
print(f"\n❌ ERROR: Empty response from {model_name} (sync)")
return False
else:
print(f"\n✅ SUCCESS: Got valid response from {model_name} (sync)")
return True
except Exception as e:
print(f"\n❌ ERROR with {model_name} (sync): {e}")
import traceback
traceback.print_exc()
return False
async def main():
print("Testing Ollama empty response fix for both sync and async...")
# Test sync methods
print("\n1. Testing SYNC methods:")
openai_sync_success = test_model_sync("openai/gpt-4o-mini")
ollama_sync_success = test_model_sync("ollama/llama3.2")
# Test async methods
print("\n2. Testing ASYNC methods:")
openai_async_success = await test_model_async("openai/gpt-4o-mini")
ollama_async_success = await test_model_async("ollama/llama3.2")
# Summary
print(f"\n{'='*60}")
print("TEST SUMMARY:")
print('='*60)
print(f"OpenAI sync test: {'✅ PASSED' if openai_sync_success else '❌ FAILED'}")
print(f"Ollama sync test: {'✅ PASSED' if ollama_sync_success else '❌ FAILED'}")
print(f"OpenAI async test: {'✅ PASSED' if openai_async_success else '❌ FAILED'}")
print(f"Ollama async test: {'✅ PASSED' if ollama_async_success else '❌ FAILED'}")
if ollama_sync_success and ollama_async_success:
print("\n🎉 Ollama empty response issue has been fixed for both sync and async!")
else:
print("\n⚠️ Ollama empty response issue still exists in some cases.")
if __name__ == "__main__":
asyncio.run(main())
@@ -0,0 +1,101 @@
#!/usr/bin/env python3
"""
Test script to verify Ollama empty response fix.
"""
import logging
from praisonaiagents import Agent, Task, PraisonAIAgents, TaskOutput
from typing import Dict, Any
# Enable debug logging
logging.basicConfig(level=logging.DEBUG)
# Define a simple tool for testing
def search_tool(query: str) -> Dict[str, Any]:
"""Simulate a search tool that returns results."""
logging.debug(f"[TEST] Search tool called with query: {query}")
results = {
"results": [
{"title": "Result 1", "description": f"Information about {query}"},
{"title": "Result 2", "description": f"More details on {query}"}
],
"total": 2
}
logging.debug(f"[TEST] Search tool returning: {results}")
return results
# Test with both OpenAI and Ollama models
def test_model(model_name: str):
print(f"\n{'='*60}")
print(f"Testing with model: {model_name}")
print('='*60)
# Create agent with the search tool
agent = Agent(
name="SearchAgent",
role="Information Researcher",
goal="Search for information and provide helpful answers",
backstory="You are an expert at finding and summarizing information.",
llm=model_name,
tools=[search_tool],
verbose=True
)
# Create a task that requires tool usage
task = Task(
name="search_task",
description="Search for information about 'Python programming' and provide a summary of what you found.",
expected_output="A clear summary of the search results",
agent=agent
)
# Create and run the workflow
workflow = PraisonAIAgents(
agents=[agent],
tasks=[task],
verbose=True
)
try:
result = workflow.start()
print(f"\n{'='*60}")
print(f"FINAL RESULT for {model_name}:")
print('='*60)
print(result)
# Check if result is empty
if not result or (isinstance(result, dict) and not result.get('task_results', {}).get('search_task', {}).get('output')):
print(f"\n❌ ERROR: Empty response from {model_name}")
return False
else:
print(f"\n✅ SUCCESS: Got valid response from {model_name}")
return True
except Exception as e:
print(f"\n❌ ERROR with {model_name}: {e}")
import traceback
traceback.print_exc()
return False
if __name__ == "__main__":
print("Testing Ollama empty response fix...")
# Test with OpenAI first (as baseline)
print("\n1. Testing with OpenAI (baseline):")
openai_success = test_model("openai/gpt-4o-mini")
# Test with Ollama
print("\n2. Testing with Ollama:")
ollama_success = test_model("ollama/llama3.2")
# Summary
print(f"\n{'='*60}")
print("TEST SUMMARY:")
print('='*60)
print(f"OpenAI test: {'✅ PASSED' if openai_success else '❌ FAILED'}")
print(f"Ollama test: {'✅ PASSED' if ollama_success else '❌ FAILED'}")
if ollama_success:
print("\n🎉 Ollama empty response issue has been fixed!")
else:
print("\n⚠️ Ollama empty response issue still exists.")
@@ -0,0 +1,67 @@
#!/usr/bin/env python3
"""
Test PostHog integration after fix.
"""
import os
import time
# Ensure telemetry is enabled
for var in ['PRAISONAI_TELEMETRY_DISABLED', 'PRAISONAI_DISABLE_TELEMETRY', 'DO_NOT_TRACK']:
if var in os.environ:
del os.environ[var]
print("=== Testing PostHog Fix ===\n")
# Test PostHog directly first
print("1. Testing PostHog directly:")
try:
from posthog import Posthog
# Create PostHog client
ph = Posthog(
project_api_key='phc_skZpl3eFLQJ4iYjsERNMbCO6jfeSJi2vyZlPahKgxZ7',
host='https://eu.i.posthog.com'
)
# Send test event
ph.capture('test-user', 'direct_test', {'timestamp': time.time()})
# Flush and shutdown properly
ph.flush()
ph.shutdown()
print("✓ Direct PostHog test successful\n")
except Exception as e:
print(f"✗ Direct PostHog test failed: {e}\n")
# Test telemetry module
print("2. Testing telemetry module:")
from praisonaiagents.telemetry.telemetry import MinimalTelemetry
# Create telemetry instance
telemetry = MinimalTelemetry(enabled=True)
# Track events
telemetry.track_agent_execution("TestAgent", success=True)
telemetry.track_task_completion("TestTask", success=True)
telemetry.track_tool_usage("TestTool", success=True)
print(f"✓ Events tracked")
print(f"✓ PostHog client available: {telemetry._posthog is not None}")
# Flush
print("\n3. Flushing telemetry...")
telemetry.flush()
print("✓ Flush completed")
# Shutdown
print("\n4. Shutting down telemetry...")
telemetry.shutdown()
print("✓ Shutdown completed")
print("\n=== Test Complete ===")
print("\nPostHog should now be receiving data properly!")
print("The fix adds:")
print("1. posthog.flush() call in the flush() method")
print("2. shutdown() method that properly closes the connection")
+2052 -2050
View File
File diff suppressed because it is too large. Load diff
+107
View File
@@ -0,0 +1,107 @@
#!/usr/bin/env python
from mcp.server.fastmcp import FastMCP
import logging
import datetime
from typing import Dict, List, Union
# Set up logging
logging.basicConfig(level=logging.INFO, filename="weather_server.log")
logger = logging.getLogger("weather-server")
# Initialize FastMCP server for weather tools
mcp = FastMCP("weather-tools")
# Mock weather data for cities
MOCK_WEATHER_DATA = {
"london": {
"temp": 15,
"feels_like": 13,
"temp_min": 12,
"temp_max": 17,
"humidity": 76,
"description": "Cloudy with occasional rain",
"wind_speed": 12,
"country": "GB"
},
"paris": {
"temp": 18,
"feels_like": 17,
"temp_min": 16,
"temp_max": 20,
"humidity": 65,
"description": "Partly cloudy",
"wind_speed": 8,
"country": "FR"
},
"new york": {
"temp": 22,
"feels_like": 24,
"temp_min": 20,
"temp_max": 25,
"humidity": 58,
"description": "Clear sky",
"wind_speed": 10,
"country": "US"
},
"tokyo": {
"temp": 26,
"feels_like": 28,
"temp_min": 24,
"temp_max": 29,
"humidity": 72,
"description": "Humid and warm",
"wind_speed": 7,
"country": "JP"
},
"sydney": {
"temp": 20,
"feels_like": 19,
"temp_min": 17,
"temp_max": 23,
"humidity": 60,
"description": "Sunny with light breeze",
"wind_speed": 15,
"country": "AU"
}
}
@mcp.tool()
def get_weather(location: Union[str, List[str]]) -> Dict:
"""Get current weather data for one or more locations.
Args:
location: City name (str) or list of city names (List[str]) to get weather for
Returns:
Dict with weather data for each location or error message
"""
def get_single_location_weather(loc: str) -> Dict:
"""Helper function to get weather for a single location"""
loc = loc.lower().strip()
if loc in MOCK_WEATHER_DATA:
weather_data = MOCK_WEATHER_DATA[loc].copy()
current_time = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
weather_data["time"] = current_time
weather_data["city"] = loc.title()
return weather_data
return {"city": loc.title(), "error": "Location not found in weather database"}
logger.info(f"Getting weather data for {location}")
# Handle list of locations
if isinstance(location, list):
results = {}
for loc in location:
if isinstance(loc, str):
results[loc] = get_single_location_weather(loc)
return {"results": results}
# Handle single location
if isinstance(location, str):
return get_single_location_weather(location)
return {"error": "Invalid location format. Please provide a string or list of strings."}
if __name__ == "__main__":
# Run the MCP server
mcp.run()
+2 -2
View File
@@ -3,8 +3,8 @@ class Praisonai < Formula
desc "AI tools for various AI applications"
homepage "https://github.com/MervinPraison/PraisonAI"
url "https://github.com/MervinPraison/PraisonAI/archive/refs/tags/v2.2.31.tar.gz"
sha256 `curl -sL https://github.com/MervinPraison/PraisonAI/archive/refs/tags/v2.2.31.tar.gz | shasum -a 256`.split.first
url "https://github.com/MervinPraison/PraisonAI/archive/refs/tags/v2.2.34.tar.gz"
sha256 `curl -sL https://github.com/MervinPraison/PraisonAI/archive/refs/tags/v2.2.34.tar.gz | shasum -a 256`.split.first
license "MIT"
depends_on "[email protected]"
+2 -2
View File
@@ -24,8 +24,8 @@ config_list = [
agent_file = "test.yaml"
actions=[
cl.Action(name="run", payload="run", label="✅ Run"),
cl.Action(name="modify", payload="modify", label="🔧 Modify"),
cl.Action(name="run", payload={"value": "run"}, label="run"),
cl.Action(name="modify", payload={"value": "modify"}, label="Modify"),
]
@cl.action_callback("run")
+5
View File
@@ -529,6 +529,7 @@ class PraisonAI:
parser.add_argument("--call", action="store_true", help="Start the PraisonAI Call server")
parser.add_argument("--public", action="store_true", help="Use ngrok to expose the server publicly (only with --call)")
parser.add_argument("--merge", action="store_true", help="Merge existing agents.yaml with auto-generated agents instead of overwriting")
parser.add_argument("--claudecode", action="store_true", help="Enable Claude Code integration for file modifications and coding tasks")
# If we're in a test environment, parse with empty args to avoid pytest interference
if in_test_env:
@@ -549,6 +550,10 @@ class PraisonAI:
if args.command == 'code':
args.ui = 'chainlit'
args.code = True
# Handle --claudecode flag for code command
if getattr(args, 'claudecode', False):
os.environ["PRAISONAI_CLAUDECODE_ENABLED"] = "true"
if args.command == 'realtime':
args.realtime = True
if args.command == 'call':
+1 -1
View File
@@ -56,7 +56,7 @@ class CloudDeployer:
file.write("FROM python:3.11-slim\n")
file.write("WORKDIR /app\n")
file.write("COPY . .\n")
file.write("RUN pip install flask praisonai==2.2.31 gunicorn markdown\n")
file.write("RUN pip install flask praisonai==2.2.34 gunicorn markdown\n")
file.write("EXPOSE 8080\n")
file.write('CMD ["gunicorn", "-b", "0.0.0.0:8080", "api:app"]\n')
+3 -3
View File
@@ -17,8 +17,8 @@ config_list = [
]
actions = [
cl.Action(name="run", payload="run", label="✅ Run"),
cl.Action(name="modify", payload="modify", label="🔧 Modify"),
cl.Action(name="run", payload={"value": "run"}, label="run"),
cl.Action(name="modify", payload={"value": "modify"}, label="Modify"),
]
@cl.action_callback("run")
@@ -819,4 +819,4 @@ async def on_settings_update(settings):
await on_settings_update(settings)
except Exception as e:
logger.error(f"Final retry failed: {str(e)}")
await cl.Message(content=f"Failed to update settings after retries: {str(e)}").send()
await cl.Message(content=f"Failed to update settings after retries: {str(e)}").send()
+244 -12
View File
@@ -13,16 +13,25 @@ from PIL import Image
from context import ContextGatherer
from tavily import TavilyClient
from crawl4ai import AsyncWebCrawler
import subprocess
# Local application/library imports
import chainlit as cl
from chainlit.input_widget import TextInput
from chainlit.input_widget import TextInput, Switch
from chainlit.types import ThreadDict
import chainlit.data as cl_data
from litellm import acompletion
import litellm
from db import DatabaseManager
# PraisonAI Agents imports
try:
from praisonaiagents import Agent
PRAISONAI_AGENTS_AVAILABLE = True
except ImportError:
PRAISONAI_AGENTS_AVAILABLE = False
# Fallback to litellm for backward compatibility
from litellm import acompletion
import litellm
# Load environment variables
load_dotenv()
@@ -41,14 +50,131 @@ logger.addHandler(console_handler)
# Set the logging level for the logger
logger.setLevel(log_level)
# Configure litellm same as in llm.py
litellm.set_verbose = False
litellm.success_callback = []
litellm._async_success_callback = []
litellm.callbacks = []
litellm.drop_params = True
litellm.modify_params = True
litellm.suppress_debug_messages = True
# Configure litellm for backward compatibility (only if praisonaiagents not available)
if not PRAISONAI_AGENTS_AVAILABLE:
import litellm
litellm.set_verbose = False
litellm.success_callback = []
litellm._async_success_callback = []
litellm.callbacks = []
litellm.drop_params = True
litellm.modify_params = True
litellm.suppress_debug_messages = True
# Claude Code Tool Function
async def claude_code_tool(query: str) -> str:
"""
Execute Claude Code CLI commands for file modifications and coding tasks.
Args:
query: The user's request that requires file modifications or coding assistance
Returns:
The output from Claude Code execution
"""
try:
# Check if the current working directory is a git repository
repo_path = os.environ.get("PRAISONAI_CODE_REPO_PATH", ".")
# Try to detect if git is available and if we're in a git repo
git_available = False
try:
subprocess.run(["git", "status"], cwd=repo_path, capture_output=True, check=True)
git_available = True
except (subprocess.CalledProcessError, FileNotFoundError):
git_available = False
# Build Claude Code command
claude_cmd = ["claude", "--dangerously-skip-permissions", "-p", query]
# Check if it's a continuation (simple heuristic)
user_session_context = cl.user_session.get("claude_code_context", False)
if user_session_context:
claude_cmd.insert(1, "--continue")
# Execute Claude Code command
result = subprocess.run(
claude_cmd,
cwd=repo_path,
capture_output=True,
text=True,
timeout=300 # 5 minutes timeout
)
# Set context for future requests
cl.user_session.set("claude_code_context", True)
output = result.stdout
if result.stderr:
output += f"\n\nErrors:\n{result.stderr}"
# If git is available and changes were made, try to create a branch and PR
if git_available and result.returncode == 0:
try:
# Check for changes
git_status = subprocess.run(
["git", "status", "--porcelain"],
cwd=repo_path,
capture_output=True,
text=True,
check=True
)
if git_status.stdout.strip():
# Create a branch for the changes
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
branch_name = f"claude-code-{timestamp}"
# Create and switch to new branch
subprocess.run(["git", "checkout", "-b", branch_name], cwd=repo_path, check=True)
# Add and commit changes
subprocess.run(["git", "add", "."], cwd=repo_path, check=True)
commit_message = f"Claude Code changes: {query[:50]}..."
subprocess.run(
["git", "commit", "-m", commit_message],
cwd=repo_path,
check=True
)
# Push to remote (if configured)
try:
subprocess.run(
["git", "push", "-u", "origin", branch_name],
cwd=repo_path,
check=True
)
# Generate PR URL (assuming GitHub)
remote_url = subprocess.run(
["git", "config", "--get", "remote.origin.url"],
cwd=repo_path,
capture_output=True,
text=True
)
if remote_url.returncode == 0:
repo_url = remote_url.stdout.strip()
if repo_url.endswith(".git"):
repo_url = repo_url[:-4]
if "github.com" in repo_url:
pr_url = f"{repo_url}/compare/main...{branch_name}?quick_pull=1"
output += f"\n\n📋 **Pull Request Created:**\n{pr_url}"
except subprocess.CalledProcessError:
output += f"\n\n🌲 **Branch created:** {branch_name} (push manually if needed)"
except subprocess.CalledProcessError as e:
output += f"\n\nGit operations failed: {e}"
return output
except subprocess.TimeoutExpired:
return "Claude Code execution timed out after 5 minutes."
except subprocess.CalledProcessError as e:
return f"Claude Code execution failed: {e}\nStdout: {e.stdout}\nStderr: {e.stderr}"
except Exception as e:
return f"Error executing Claude Code: {str(e)}"
CHAINLIT_AUTH_SECRET = os.getenv("CHAINLIT_AUTH_SECRET")
@@ -109,6 +235,12 @@ async def start():
model_name = os.getenv("MODEL_NAME", "gpt-4o-mini")
cl.user_session.set("model_name", model_name)
logger.debug(f"Model name: {model_name}")
# Load Claude Code setting (check CLI flag first, then database setting)
claude_code_enabled = os.getenv("PRAISONAI_CLAUDECODE_ENABLED", "false").lower() == "true"
if not claude_code_enabled:
claude_code_enabled = (load_setting("claude_code_enabled") or "false").lower() == "true"
settings = cl.ChatSettings(
[
TextInput(
@@ -116,6 +248,11 @@ async def start():
label="Enter the Model Name",
placeholder="e.g., gpt-4o-mini",
initial=model_name
),
Switch(
id="claude_code_enabled",
label="Enable Claude Code (file modifications & coding)",
initial=claude_code_enabled
)
]
)
@@ -134,10 +271,13 @@ async def setup_agent(settings):
logger.debug(settings)
cl.user_session.set("settings", settings)
model_name = settings["model_name"]
claude_code_enabled = settings.get("claude_code_enabled", False)
cl.user_session.set("model_name", model_name)
cl.user_session.set("claude_code_enabled", claude_code_enabled)
# Save in settings table
save_setting("model_name", model_name)
save_setting("claude_code_enabled", str(claude_code_enabled).lower())
# Save in thread metadata
thread_id = cl.user_session.get("thread_id")
@@ -152,6 +292,7 @@ async def setup_agent(settings):
metadata = {}
metadata["model_name"] = model_name
metadata["claude_code_enabled"] = claude_code_enabled
# Always store metadata as a dictionary
await cl_data._data_layer.update_thread(thread_id, metadata=metadata)
@@ -221,6 +362,7 @@ tools = [{
@cl.on_message
async def main(message: cl.Message):
model_name = load_setting("model_name") or os.getenv("MODEL_NAME") or "gpt-4o-mini"
claude_code_enabled = cl.user_session.get("claude_code_enabled", False)
message_history = cl.user_session.get("message_history", [])
repo_path_to_use = os.environ.get("PRAISONAI_CODE_REPO_PATH", ".")
gatherer = ContextGatherer(directory=repo_path_to_use)
@@ -258,6 +400,87 @@ Context:
msg = cl.Message(content="")
await msg.send()
# Use PraisonAI Agents if available, otherwise fallback to litellm
if PRAISONAI_AGENTS_AVAILABLE:
await handle_with_praisonai_agents(message, user_message, model_name, claude_code_enabled, msg, image)
else:
await handle_with_litellm(user_message, model_name, message_history, msg, image)
async def handle_with_praisonai_agents(message, user_message, model_name, claude_code_enabled, msg, image):
"""Handle message using PraisonAI Agents framework with optional Claude Code tool"""
try:
# Prepare tools list
available_tools = []
# Add Tavily search tool if API key available
if tavily_api_key:
available_tools.append(tavily_web_search)
# Add Claude Code tool if enabled
if claude_code_enabled:
available_tools.append(claude_code_tool)
# Create agent instructions
instructions = """You are a helpful AI assistant. Use the available tools when needed to provide comprehensive responses.
If Claude Code tool is available and the user's request involves:
- File modifications, code changes, or implementation tasks
- Creating, editing, or debugging code
- Project setup or development tasks
- Git operations or version control
Then use the Claude Code tool to handle those requests.
For informational questions, explanations, or general conversations, respond normally without using Claude Code."""
# Create agent
agent = Agent(
name="PraisonAI Assistant",
instructions=instructions,
llm=model_name,
tools=available_tools if available_tools else None
)
# Execute agent with streaming
full_response = ""
# Use agent's streaming capabilities if available
try:
# For now, use synchronous execution and stream the result
# TODO: Implement proper streaming when PraisonAI agents support it
result = agent.start(user_message)
# Stream the response character by character for better UX
if hasattr(result, 'raw'):
response_text = result.raw
else:
response_text = str(result)
for char in response_text:
await msg.stream_token(char)
full_response += char
# Small delay to make streaming visible
await asyncio.sleep(0.01)
except Exception as e:
error_response = f"Error executing agent: {str(e)}"
for char in error_response:
await msg.stream_token(char)
full_response += char
await asyncio.sleep(0.01)
msg.content = full_response
await msg.update()
except Exception as e:
error_msg = f"Failed to use PraisonAI Agents: {str(e)}"
logger.error(error_msg)
await msg.stream_token(error_msg)
msg.content = error_msg
await msg.update()
async def handle_with_litellm(user_message, model_name, message_history, msg, image):
"""Fallback handler using litellm for backward compatibility"""
# Prepare the completion parameters using the helper function
completion_params = _build_completion_params(
model_name,
@@ -279,7 +502,7 @@ Context:
]
}
# Use a vision-capable model when an image is present
completion_params["model"] = "gpt-4-vision-preview" # Adjust this to your actual vision-capable model
completion_params["model"] = "gpt-4-vision-preview"
# Only add tools and tool_choice if Tavily API key is available and no image is uploaded
if tavily_api_key:
@@ -412,6 +635,10 @@ async def send_count():
async def on_chat_resume(thread: ThreadDict):
logger.info(f"Resuming chat: {thread['id']}")
model_name = load_setting("model_name") or os.getenv("MODEL_NAME") or "gpt-4o-mini"
# Load Claude Code setting (check CLI flag first, then database setting)
claude_code_enabled = os.getenv("PRAISONAI_CLAUDECODE_ENABLED", "false").lower() == "true"
if not claude_code_enabled:
claude_code_enabled = (load_setting("claude_code_enabled") or "false").lower() == "true"
logger.debug(f"Model name: {model_name}")
settings = cl.ChatSettings(
[
@@ -420,6 +647,11 @@ async def on_chat_resume(thread: ThreadDict):
label="Enter the Model Name",
placeholder="e.g., gpt-4o-mini",
initial=model_name
),
Switch(
id="claude_code_enabled",
label="Enable Claude Code (file modifications & coding)",
initial=claude_code_enabled
)
]
)
+4 -4
View File
@@ -1,6 +1,6 @@
[project]
name = "PraisonAI"
version = "2.2.31"
version = "2.2.34"
description = "PraisonAI is an AI Agents Framework with Self Reflection. PraisonAI application combines PraisonAI Agents, AutoGen, and CrewAI into a low-code solution for building and managing multi-agent LLM systems, focusing on simplicity, customisation, and efficient human-agent collaboration."
readme = "README.md"
license = ""
@@ -12,7 +12,7 @@ dependencies = [
"rich>=13.7",
"markdown>=3.5",
"pyparsing>=3.0.0",
"praisonaiagents>=0.0.104",
"praisonaiagents>=0.0.107",
"python-dotenv>=0.19.0",
"instructor>=1.3.3",
"PyYAML>=6.0",
@@ -95,7 +95,7 @@ autogen = ["pyautogen>=0.2.19", "praisonai-tools>=0.0.15", "crewai"]
[tool.poetry]
name = "PraisonAI"
version = "2.2.31"
version = "2.2.34"
description = "PraisonAI is an AI Agents Framework with Self Reflection. PraisonAI application combines PraisonAI Agents, AutoGen, and CrewAI into a low-code solution for building and managing multi-agent LLM systems, focusing on simplicity, customisation, and efficient human-agent collaboration."
authors = ["Mervin Praison"]
license = ""
@@ -113,7 +113,7 @@ python = ">=3.10,<3.13"
rich = ">=13.7"
markdown = ">=3.5"
pyparsing = ">=3.0.0"
praisonaiagents = ">=0.0.104"
praisonaiagents = ">=0.0.107"
python-dotenv = ">=0.19.0"
instructor = ">=1.3.3"
PyYAML = ">=6.0"
@@ -0,0 +1,291 @@
# Claude Code Integration with PraisonAI Agents
This document describes the integration of Claude Code with PraisonAI Agents, allowing AI agents to intelligently decide when to use Claude Code for file modifications and coding tasks.
## Overview
The refactored implementation replaces direct `litellm` usage with `praisonaiagents`, making Claude Code a custom tool that the AI agent can choose to use based on the user's request. This provides better intelligence and flexibility while maintaining backward compatibility.
## Key Features
### 🤖 Agent-Driven Decision Making
- AI agent intelligently decides when to use Claude Code vs. regular responses
- No manual detection logic - the agent understands context
- Automatic tool selection based on request type
### 🔧 Claude Code as a Custom Tool
- Claude Code is implemented as a tool function for PraisonAI Agents
- Executes `claude --dangerously-skip-permissions -p "query"`
- Supports `--continue` flag for conversation continuity
- Git operations with automatic branch creation and PR URLs
### ⚙️ Flexible Configuration
- CLI flag: `praisonai code --claudecode`
- UI toggle: "Enable Claude Code (file modifications & coding)"
- Environment variable: `PRAISONAI_CLAUDECODE_ENABLED=true`
### 🔄 Backward Compatibility
- Falls back to `litellm` if `praisonaiagents` is not available
- Maintains all existing functionality
- No breaking changes to existing workflows
## Architecture
### Agent Instructions
The agent receives these instructions to guide tool usage:
```
You are a helpful AI assistant. Use the available tools when needed to provide comprehensive responses.
If Claude Code tool is available and the user's request involves:
- File modifications, code changes, or implementation tasks
- Creating, editing, or debugging code
- Project setup or development tasks
- Git operations or version control
Then use the Claude Code tool to handle those requests.
For informational questions, explanations, or general conversations, respond normally without using Claude Code.
```
### Tool Function: `claude_code_tool`
```python
async def claude_code_tool(query: str) -> str:
"""
Execute Claude Code CLI commands for file modifications and coding tasks.
Args:
query: The user's request that requires file modifications or coding assistance
Returns:
The output from Claude Code execution
"""
```
**Features:**
- Executes Claude Code with `--dangerously-skip-permissions`
- Supports conversation continuity with `--continue` flag
- Automatic git branch creation and management
- PR URL generation for GitHub repositories
- 5-minute timeout for long operations
- Comprehensive error handling
### Available Tools
When Claude Code is enabled, the agent has access to:
1. **Claude Code Tool** - For file modifications and coding tasks
2. **Tavily Web Search** - For internet research (if API key configured)
The agent decides which tool(s) to use based on the user's request.
## Usage
### Command Line Interface
```bash
# Enable Claude Code integration
praisonai code --claudecode
# Use regular mode (no Claude Code)
praisonai code
```
### Environment Variables
```bash
# Force enable Claude Code (overrides UI setting)
export PRAISONAI_CLAUDECODE_ENABLED=true
# Set repository path (defaults to current directory)
export PRAISONAI_CODE_REPO_PATH=/path/to/your/repo
```
### UI Settings
In the PraisonAI Code UI, you can:
- Toggle "Enable Claude Code (file modifications & coding)" switch
- Setting is saved to database for persistence
- CLI flag takes precedence over UI setting
## Examples
### File Modification Request
**User:** "Create a new Python function to calculate fibonacci numbers"
**Agent Decision:** Uses Claude Code tool → Creates/modifies files → Returns implementation details
### Informational Request
**User:** "How does fibonacci algorithm work?"
**Agent Decision:** Responds normally → Provides explanation without file modifications
### Mixed Request
**User:** "Explain how sorting works and implement quicksort in Python"
**Agent Decision:** May use Claude Code tool for implementation → Provides both explanation and code files
## Git Integration
When Claude Code makes changes and git is available:
1. **Automatic Branch Creation:** Creates `claude-code-YYYYMMDD_HHMMSS` branch
2. **Commit Changes:** Commits all modifications with descriptive message
3. **Remote Push:** Pushes branch to remote repository (if configured)
4. **PR URL Generation:** Generates GitHub PR creation URL
Example output:
```
📋 **Pull Request Created:**
https://github.com/user/repo/compare/main...claude-code-20241210_143022?quick_pull=1
```
## Error Handling
### Graceful Degradation
- If `praisonaiagents` unavailable → Falls back to `litellm`
- If Claude Code CLI unavailable → Agent works without the tool
- If git unavailable → Code changes without git operations
- Network issues → Continues with local operations
### Error Messages
- Clear error reporting in streaming responses
- Timeout handling for long operations
- Detailed logging for debugging
## Implementation Details
### File Structure
```
src/praisonai/praisonai/
├── cli.py # Added --claudecode flag
└── ui/
└── code.py # Refactored to use praisonaiagents
```
### Key Functions
1. **`handle_with_praisonai_agents()`** - Main agent execution handler
2. **`handle_with_litellm()`** - Fallback for backward compatibility
3. **`claude_code_tool()`** - Claude Code tool implementation
4. **Settings management** - UI toggles and persistence
### Dependencies
**Required:**
- `praisonaiagents` - Core agent framework
- `subprocess` - For Claude Code CLI execution
- `chainlit` - UI framework
**Optional:**
- `tavily` - Web search capability
- `git` - Version control operations
- `claude` CLI - File modification capabilities
## Testing
Use the included test script to verify the integration:
```bash
python test_claude_code_integration.py
```
Tests verify:
- Import functionality
- PraisonAI Agents availability
- Claude Code CLI availability
- Environment variable configuration
- Basic tool execution
## Migration Guide
### From Previous Implementation
The previous implementation used direct Claude Code detection logic. The new implementation:
1. **Replaces detection logic** with agent intelligence
2. **Maintains same UI/CLI interfaces** for easy migration
3. **Preserves all existing functionality** while adding flexibility
4. **Requires no user workflow changes**
### Upgrading
1. Ensure `praisonaiagents` is installed
2. Update PraisonAI to include the refactored code
3. Use `--claudecode` flag or UI toggle as before
4. Existing settings and workflows continue working
## Best Practices
### When to Enable Claude Code
- File modification projects
- Code development workflows
- Repository maintenance tasks
- Implementation and debugging sessions
### When to Disable Claude Code
- Read-only analysis
- Documentation-only sessions
- Learning and educational content
- General Q&A conversations
### Configuration Recommendations
- Use CLI flag for development sessions
- Use UI toggle for mixed workflows
- Set environment variables for CI/CD integration
- Configure repository path for multi-project setups
## Troubleshooting
### Common Issues
**Agent doesn't use Claude Code tool:**
- Verify Claude Code is enabled (`--claudecode` flag or UI toggle)
- Check that request involves file modifications
- Ensure `praisonaiagents` is installed
**Claude Code tool fails:**
- Verify `claude` CLI is installed and in PATH
- Check repository permissions
- Confirm git repository status (if git operations needed)
**Fallback to litellm:**
- Install `praisonaiagents`: `pip install praisonaiagents`
- Check import errors in logs
- Verify Python environment compatibility
### Debug Information
Enable verbose logging:
```bash
export LOGLEVEL=DEBUG
praisonai code --claudecode
```
Check environment:
```python
import os
print("Claude Code enabled:", os.getenv("PRAISONAI_CLAUDECODE_ENABLED"))
print("Repo path:", os.getenv("PRAISONAI_CODE_REPO_PATH"))
```
## Future Enhancements
### Planned Features
- Real-time streaming from PraisonAI Agents
- Enhanced git workflow integration
- Multi-repository support
- Advanced tool coordination
- Performance optimizations
### Extension Points
- Additional coding tools integration
- Custom agent instructions
- Workflow templates
- Integration with other development tools
---
For technical support or questions, please refer to the main PraisonAI documentation or submit issues to the repository.
@@ -0,0 +1,138 @@
#!/usr/bin/env python3
"""
Test script for Claude Code integration with PraisonAI Agents
This script tests the basic functionality of the refactored Claude Code integration
"""
import os
import sys
import asyncio
import unittest
# Add the src directory to the path for imports
sys.path.insert(0, os.path.join(os.path.dirname(__file__), 'src', 'praisonai'))
def test_claude_code_tool_import():
"""Test that we can import the Claude Code tool function"""
try:
from praisonai.ui.code import claude_code_tool
print("✅ Successfully imported claude_code_tool")
return True
except ImportError as e:
print(f"❌ Failed to import claude_code_tool: {e}")
return False
def test_praisonai_agents_import():
"""Test praisonaiagents import availability"""
try:
from praisonaiagents import Agent
print("✅ PraisonAI Agents is available")
return True
except ImportError as e:
print(f"⚠️ PraisonAI Agents not available (fallback to litellm): {e}")
return False
def test_claude_code_availability():
"""Test if Claude Code CLI is available"""
import subprocess
try:
result = subprocess.run(['claude', '--version'], capture_output=True, text=True, timeout=10)
if result.returncode == 0:
print(f"✅ Claude Code CLI is available: {result.stdout.strip()}")
return True
else:
print(f"❌ Claude Code CLI returned error: {result.stderr}")
return False
except FileNotFoundError:
print("⚠️ Claude Code CLI not found in PATH")
return False
except subprocess.TimeoutExpired:
print("⚠️ Claude Code CLI check timed out")
return False
except Exception as e:
print(f"⚠️ Error checking Claude Code CLI: {e}")
return False
async def test_claude_code_tool_execution():
"""Test basic Claude Code tool execution (simple query)"""
try:
from praisonai.ui.code import claude_code_tool
# Test with a simple query that shouldn't modify files
test_query = "What is the current directory?"
result = await claude_code_tool(test_query)
print(f"✅ Claude Code tool executed successfully")
print(f"Query: {test_query}")
print(f"Result (first 100 chars): {str(result)[:100]}...")
return True
except Exception as e:
print(f"❌ Claude Code tool execution failed: {e}")
return False
def test_environment_variables():
"""Test that environment variables are properly set"""
test_vars = [
"PRAISONAI_CLAUDECODE_ENABLED",
"PRAISONAI_CODE_REPO_PATH"
]
print("Environment Variables:")
for var in test_vars:
value = os.getenv(var, "NOT_SET")
print(f" {var}: {value}")
return True
async def run_tests():
"""Run all tests"""
print("🧪 Testing Claude Code Integration with PraisonAI Agents")
print("=" * 60)
tests = [
("Import Claude Code Tool", test_claude_code_tool_import),
("Import PraisonAI Agents", test_praisonai_agents_import),
("Environment Variables", test_environment_variables),
("Claude Code CLI Availability", test_claude_code_availability),
]
results = {}
for test_name, test_func in tests:
print(f"\n🔍 {test_name}:")
try:
results[test_name] = test_func()
except Exception as e:
print(f"❌ Test failed with exception: {e}")
results[test_name] = False
# Only test Claude Code tool execution if CLI is available
if results.get("Claude Code CLI Availability", False):
print(f"\n🔍 Claude Code Tool Execution:")
try:
results["Claude Code Tool Execution"] = await test_claude_code_tool_execution()
except Exception as e:
print(f"❌ Test failed with exception: {e}")
results["Claude Code Tool Execution"] = False
# Summary
print("\n" + "=" * 60)
print("📊 Test Summary:")
passed = sum(1 for result in results.values() if result)
total = len(results)
for test_name, result in results.items():
status = "✅ PASS" if result else "❌ FAIL"
print(f" {status} {test_name}")
print(f"\nResults: {passed}/{total} tests passed")
if passed == total:
print("🎉 All tests passed! Integration is working correctly.")
else:
print("⚠️ Some tests failed. Please check the implementation.")
return passed == total
if __name__ == "__main__":
asyncio.run(run_tests())
@@ -0,0 +1,128 @@
#!/usr/bin/env python3
"""
Quick test for the remote agent connectivity feature.
"""
import sys
import os
sys.path.insert(0, os.path.join(os.path.dirname(__file__), 'src', 'praisonai-agents'))
from praisonaiagents import Session
def test_remote_session_creation():
"""Test creating a remote session."""
print("🧪 Testing remote session creation...")
try:
# This should fail gracefully since there's no server running
session = Session(agent_url="localhost:8000/agent")
print(f"❌ Unexpected: Session created without server: {session}")
except ConnectionError as e:
print(f"✅ Expected connection error: {e}")
except Exception as e:
print(f"❌ Unexpected error: {e}")
return False
return True
def test_local_session_backwards_compatibility():
"""Test that local sessions still work as before."""
print("\n🧪 Testing local session backwards compatibility...")
try:
# This should work as before
session = Session(session_id="test_local")
print(f"✅ Local session created: {session}")
# Test that it's not remote
if session.is_remote:
print("❌ Local session incorrectly marked as remote")
return False
print("✅ Local session correctly identified")
return True
except Exception as e:
print(f"❌ Error creating local session: {e}")
return False
def test_remote_session_restrictions():
"""Test that remote sessions properly restrict local operations."""
print("\n🧪 Testing remote session restrictions...")
try:
# Create a mock remote session (will fail connection but that's OK for testing restrictions)
session = Session(agent_url="mock://fake-server:8000/agent")
except ConnectionError:
# Create the session object manually for testing restrictions
session = Session.__new__(Session)
session.session_id = "test_remote"
session.user_id = "test_user"
session.agent_url = "mock://fake-server:8000/agent"
session.timeout = 30
session.is_remote = True
session.memory_config = {}
session.knowledge_config = {}
session._memory = None
session._knowledge = None
session._agents_instance = None
# Test memory restriction
try:
_ = session.memory
print("❌ Memory access should be restricted for remote sessions")
return False
except ValueError as e:
print(f"✅ Memory properly restricted: {e}")
# Test knowledge restriction
try:
_ = session.knowledge
print("❌ Knowledge access should be restricted for remote sessions")
return False
except ValueError as e:
print(f"✅ Knowledge properly restricted: {e}")
# Test agent creation restriction
try:
session.Agent(name="Test", role="Assistant")
print("❌ Agent creation should be restricted for remote sessions")
return False
except ValueError as e:
print(f"✅ Agent creation properly restricted: {e}")
return True
def main():
"""Run all tests."""
print("🚀 Testing Remote Agent Connectivity Implementation")
print("=" * 60)
tests = [
test_remote_session_creation,
test_local_session_backwards_compatibility,
test_remote_session_restrictions
]
passed = 0
total = len(tests)
for test in tests:
if test():
passed += 1
else:
print("❌ Test failed!")
print("\n" + "=" * 60)
print(f"📊 Test Results: {passed}/{total} tests passed")
if passed == total:
print("🎉 All tests passed! Remote agent connectivity is working correctly.")
return True
else:
print("⚠️ Some tests failed. Check the implementation.")
return False
if __name__ == "__main__":
success = main()
sys.exit(0 if success else 1)
+2584 -2582
View File
File diff suppressed because it is too large. Load diff