Spaces:
Sleeping
Sleeping
import streamlit as st | |
import json | |
import os | |
import io | |
import base64 | |
import boto3 | |
from PIL import Image | |
from streamlit_tags import st_tags | |
# Load AWS credentials using correct HF Secrets | |
AWS_ACCESS_KEY = os.getenv("AWS_ACCESS_KEY") | |
AWS_SECRET_KEY = os.getenv("AWS_SECRET_KEY") | |
AWS_REGION = os.getenv("AWS_REGION", "us-east-1") | |
S3_BUCKET_NAME = os.getenv("S3_BUCKET_NAME", "food-image-crowdsourcing") | |
DYNAMODB_TABLE = os.getenv("DYNAMODB_TABLE", "image_metadata") | |
# Load Firebase credentials | |
FIREBASE_CONFIG = json.loads(os.getenv("FIREBASE_CONFIG", "{}")) | |
# Initialize AWS Services (S3 & DynamoDB) | |
s3 = boto3.client( | |
"s3", | |
aws_access_key_id=AWS_ACCESS_KEY, | |
aws_secret_access_key=AWS_SECRET_KEY, | |
) | |
dynamodb = boto3.resource( | |
"dynamodb", | |
region_name=AWS_REGION, | |
aws_access_key_id=AWS_ACCESS_KEY, | |
aws_secret_access_key=AWS_SECRET_KEY, | |
) | |
metadata_table = dynamodb.Table(DYNAMODB_TABLE) | |
# Streamlit Layout - Three Panel Design | |
st.title("๐ฝ๏ธ Food Image Review & Annotation") | |
col1, col2, col3 = st.columns([1, 1, 1]) # Equal size columns | |
# Upload Image | |
uploaded_file = st.file_uploader("Upload an image of your food", type=["jpg", "png", "jpeg"]) | |
if uploaded_file: | |
image = Image.open(uploaded_file) | |
st.session_state["original_image"] = image | |
# Resize image in Streamlit before sending to S3 | |
def resize_image(image): | |
aspect_ratio = image.width / image.height | |
new_width = 512 | |
new_height = int(new_width / aspect_ratio) | |
resized_image = image.resize((new_width, new_height)) | |
return resized_image | |
if "original_image" in st.session_state: | |
original_img = st.session_state["original_image"] | |
processed_img = resize_image(original_img) | |
# ๐ผ๏ธ Panel 1: Original Image | |
with col1: | |
st.subheader("๐ท Original Image") | |
st.image(original_img, caption="Uploaded", use_container_width=True) | |
# ๐ผ๏ธ Panel 2: Resized Image (512x512 Maintaining Aspect Ratio) | |
with col2: | |
st.subheader("๐ผ๏ธ Processed Image") | |
st.image(processed_img, caption="512x512 Maintained Aspect", use_container_width=True) | |
# โ๏ธ Panel 3: Food Annotations with Intellisense | |
with col3: | |
st.subheader("๐ Add Annotations") | |
# Expanded food suggestions | |
suggested_foods = [ | |
"Pizza", "Pasta", "Tacos", "Sushi", "Ramen", "Kimchi", "Bratwurst", "Jambalaya", | |
"Chicken", "Rice", "Steak", "Bread", "Cheese", "Salmon", "Avocado", "Eggs", | |
"Carrots", "Tomatoes", "Cucumber", "Yogurt", "Peanuts", "Lettuce", "Pierogies", "Mongolian Beef", "Spaghetti Bolognese", | |
"Bigos", "Stuffed Cabbage", "Zurek", "Schnitzel", "Tomato Soup", "Potato Pancakes", "Blintzes", "Broccoli Chicken" | |
] | |
# User selects food items from suggestions | |
food_items = st_tags( | |
label="Enter food items", | |
text="Add items...", | |
value=[], | |
suggestions=suggested_foods, | |
maxtags=10, | |
) | |
if st.button("Save Annotations"): | |
metadata_table.update_item( | |
Key={"image_id": uploaded_file.name}, | |
UpdateExpression="SET annotations = :a, processing_status = :p, s3_url = :s, tokens_earned = :t", | |
ExpressionAttributeValues={ | |
":a": food_items, | |
":p": "processed", | |
":s": f"s3://{S3_BUCKET_NAME}/raw-uploads/{uploaded_file.name}", | |
":t": 1 if food_items else 0 | |
}, | |
) | |
st.success("โ Annotations saved successfully!") | |