Update app.py
Browse files
app.py
CHANGED
@@ -497,7 +497,7 @@ class NFTProcessor:
|
|
497 |
except Exception as e:
|
498 |
logger.error(f"Error processing image: {e}")
|
499 |
return None
|
500 |
-
class ChatInterface:
|
501 |
"""Manages chat interactions and context."""
|
502 |
|
503 |
def __init__(self, openai_key: str, etherscan_key: str, opensea_key: str):
|
@@ -661,6 +661,122 @@ class ChatInterface:
|
|
661 |
await self.nft_processor.__aexit__(None, None, None)
|
662 |
self.nft_processor = None
|
663 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
664 |
def main():
|
665 |
"""Main entry point."""
|
666 |
demo = create_gradio_interface()
|
|
|
497 |
except Exception as e:
|
498 |
logger.error(f"Error processing image: {e}")
|
499 |
return None
|
500 |
+
class ChatInterface:
|
501 |
"""Manages chat interactions and context."""
|
502 |
|
503 |
def __init__(self, openai_key: str, etherscan_key: str, opensea_key: str):
|
|
|
661 |
await self.nft_processor.__aexit__(None, None, None)
|
662 |
self.nft_processor = None
|
663 |
|
664 |
+
def create_gradio_interface() -> gr.Blocks:
|
665 |
+
"""Create Gradio web interface."""
|
666 |
+
chat_interface = None
|
667 |
+
|
668 |
+
with gr.Blocks(theme=gr.themes.Soft()) as demo:
|
669 |
+
gr.Markdown("""
|
670 |
+
# π LOSS DOG: Blockchain Wallet Analyzer
|
671 |
+
|
672 |
+
Enter your API keys and chat with your friendly blockchain-sniffing puppy!
|
673 |
+
- Paste an Ethereum address to analyze
|
674 |
+
- Chat about the wallet contents
|
675 |
+
- View NFT images in the gallery
|
676 |
+
""")
|
677 |
+
|
678 |
+
with gr.Row():
|
679 |
+
openai_key = gr.Textbox(
|
680 |
+
label="OpenAI API Key",
|
681 |
+
type="password",
|
682 |
+
placeholder="sk-..."
|
683 |
+
)
|
684 |
+
etherscan_key = gr.Textbox(
|
685 |
+
label="Etherscan API Key",
|
686 |
+
type="password",
|
687 |
+
placeholder="Enter Etherscan key..."
|
688 |
+
)
|
689 |
+
opensea_key = gr.Textbox(
|
690 |
+
label="OpenSea API Key",
|
691 |
+
type="password",
|
692 |
+
placeholder="Enter OpenSea key..."
|
693 |
+
)
|
694 |
+
|
695 |
+
validation_status = gr.Textbox(label="Status", interactive=False)
|
696 |
+
validate_btn = gr.Button("Validate Keys", variant="primary")
|
697 |
+
|
698 |
+
with gr.Row():
|
699 |
+
with gr.Column(scale=2):
|
700 |
+
chatbot = gr.Chatbot(
|
701 |
+
label="Chat with LOSS DOG π",
|
702 |
+
height=500,
|
703 |
+
bubble_full_width=False
|
704 |
+
)
|
705 |
+
with gr.Row():
|
706 |
+
msg_input = gr.Textbox(
|
707 |
+
label="Message",
|
708 |
+
placeholder="Enter ETH address or ask about the wallet...",
|
709 |
+
scale=8
|
710 |
+
)
|
711 |
+
send_btn = gr.Button("Send", scale=1, variant="primary")
|
712 |
+
clear_btn = gr.Button("Clear", scale=1)
|
713 |
+
|
714 |
+
with gr.Column(scale=1):
|
715 |
+
nft_gallery = gr.Gallery(
|
716 |
+
label="NFT Gallery",
|
717 |
+
columns=2,
|
718 |
+
height=400
|
719 |
+
)
|
720 |
+
wallet_data = gr.JSON(label="Wallet Data")
|
721 |
+
|
722 |
+
def init_interface(openai_k: str, etherscan_k: str, opensea_k: str) -> str:
|
723 |
+
"""Initialize chat interface with API keys."""
|
724 |
+
nonlocal chat_interface
|
725 |
+
try:
|
726 |
+
chat_interface = ChatInterface(openai_k, etherscan_k, opensea_k)
|
727 |
+
return "β
API keys validated successfully!"
|
728 |
+
except Exception as e:
|
729 |
+
return f"β Error: {str(e)}"
|
730 |
+
|
731 |
+
async def process_message(
|
732 |
+
message: str,
|
733 |
+
history: List[Tuple[str, str]]
|
734 |
+
) -> Tuple[List[Tuple[str, str]], Dict[str, Any], List[Image.Image]]:
|
735 |
+
"""Process user message."""
|
736 |
+
if not chat_interface:
|
737 |
+
return [], {}, []
|
738 |
+
return await chat_interface.process_message(message, history)
|
739 |
+
|
740 |
+
def clear_chat():
|
741 |
+
"""Clear chat and context."""
|
742 |
+
if chat_interface:
|
743 |
+
return chat_interface.clear_context()
|
744 |
+
return {}, []
|
745 |
+
|
746 |
+
# Wire up the interface
|
747 |
+
validate_btn.click(
|
748 |
+
init_interface,
|
749 |
+
inputs=[openai_key, etherscan_key, opensea_key],
|
750 |
+
outputs=[validation_status]
|
751 |
+
)
|
752 |
+
|
753 |
+
msg_input.submit(
|
754 |
+
process_message,
|
755 |
+
inputs=[msg_input, chatbot],
|
756 |
+
outputs=[chatbot, wallet_data, nft_gallery]
|
757 |
+
).then(
|
758 |
+
lambda: gr.update(value=""),
|
759 |
+
None,
|
760 |
+
[msg_input]
|
761 |
+
)
|
762 |
+
|
763 |
+
send_btn.click(
|
764 |
+
process_message,
|
765 |
+
inputs=[msg_input, chatbot],
|
766 |
+
outputs=[chatbot, wallet_data, nft_gallery]
|
767 |
+
).then(
|
768 |
+
lambda: gr.update(value=""),
|
769 |
+
None,
|
770 |
+
[msg_input]
|
771 |
+
)
|
772 |
+
|
773 |
+
clear_btn.click(
|
774 |
+
clear_chat,
|
775 |
+
outputs=[wallet_data, chatbot]
|
776 |
+
)
|
777 |
+
|
778 |
+
return demo
|
779 |
+
|
780 |
def main():
|
781 |
"""Main entry point."""
|
782 |
demo = create_gradio_interface()
|