import os
import shutil
import subprocess
import zipfile
import time
import torch
import torch.nn as nn
import torch.optim as optim
from torchvision import datasets, transforms, models
from torch.optim import lr_scheduler
import subprocess
import zipfile
from PIL import Image
import gradio as gr
import requests
from io import BytesIO
# Setup Kaggle API
kaggle_dir = os.path.expanduser("~/.kaggle")
if not os.path.exists(kaggle_dir):
os.makedirs(kaggle_dir)
# Copy the kaggle.json file to the ~/.kaggle directory
kaggle_json_path = "kaggle.json"
kaggle_dest_path = os.path.join(kaggle_dir, "kaggle.json")
if not os.path.exists(kaggle_dest_path):
shutil.copy(kaggle_json_path, kaggle_dest_path)
os.chmod(kaggle_dest_path, 0o600)
print("Kaggle API key copied and permissions set.")
else:
print("Kaggle API key already exists.")
# Download the dataset from Kaggle using Kaggle CLI
dataset_name = "mostafaabla/garbage-classification"
print(f"Downloading the dataset: {dataset_name}")
download_command = f"kaggle datasets download -d {dataset_name}"
# Run the download command
subprocess.run(download_command, shell=True)
# Unzip the downloaded dataset
dataset_zip = "garbage-classification.zip"
extracted_folder = "./garbage-classification"
# Check if the zip file exists
if os.path.exists(dataset_zip):
if not os.path.exists(extracted_folder):
with zipfile.ZipFile(dataset_zip, 'r') as zip_ref:
zip_ref.extractall(extracted_folder)
print("Dataset unzipped successfully!")
else:
print("Dataset already unzipped.")
else:
print(f"Dataset zip file '{dataset_zip}' not found.")
# Model training and testing in separate directory at ipynb file (Copy of ai-portfolio Kendrick.ipynb)
# Load model
def load_model():
model = models.resnet50(weights='DEFAULT') # Using default weights for initialization
num_ftrs = model.fc.in_features
model.fc = nn.Linear(num_ftrs, 12) # Adjust to the number of classes you have
# Load the state dict
model.load_state_dict(torch.load('resnet50_garbage_classificationv1.2.pth', map_location=torch.device('cpu')))
model.eval() # Set to evaluation mode
return model
# Load the model
model = load_model()
# Define image transformations
transform = transforms.Compose([
transforms.Resize(256),
transforms.CenterCrop(224),
transforms.ToTensor(),
transforms.Normalize([0.485, 0.456, 0.406], [0.229, 0.224, 0.225])
])
# Class names and corresponding bin images
class_names = ['battery', 'biological', 'brown-glass', 'cardboard',
'clothes', 'green-glass', 'metal', 'paper',
'plastic', 'shoes', 'trash', 'white-glass']
# Define bin colors and image paths
bin_info = {
'battery': ('Merah (Red)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/red_bin.png'),
'biological': ('Hijau (Green)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/green_bin.png'),
'brown-glass': ('Kuning (Yellow) / Bank Sampah (Recycling center/ Trash Banks)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'cardboard': ('Biru (Blue)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/blue_bin.png'),
'clothes': ('Kuning (Yellow) / Bank Sampah (Recycling center/ Trash Banks)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'green-glass': ('Kuning (Yellow) / Bank Sampah (Recycling center/ Trash Banks)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'metal': ('Kuning (Yellow)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'paper': ('Biru (Blue)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/blue_bin.png'),
'plastic': ('Kuning (Yellow)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'shoes': ('Kuning (Yellow) / Bank Sampah (Recycling center/ Trash Banks)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png'),
'trash': ('Abu-abu (Gray)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/gray_bin.png'),
'white-glass': ('Kuning (Yellow) / Bank Sampah (Recycling center/ Trash Banks)', 'https://huggingface.co/spaces/kendrickfff/resnet50_garbage_classification_v1.2/resolve/main/yellow_bin.png')
}
# Define the prediction function
def predict(image):
image = Image.fromarray(image) # Convert numpy array to PIL Image
image = transform(image) # Apply transformations
image = image.unsqueeze(0) # Add batch dimension
with torch.no_grad():
outputs = model(image)
_, predicted = torch.max(outputs, 1)
class_name = class_names[predicted.item()] # Return predicted class name
bin_color, bin_image = bin_info[class_name] # Get bin color and image
return class_name, bin_color, bin_image # Return class name, bin color, and bin image
# Gradio interface with 3 outputs
iface = gr.Interface(
fn=predict,
inputs=gr.Image(type="numpy", label="Unggah Gambar"),
outputs=[
gr.Textbox(label="Jenis Sampah"),
gr.Textbox(label="Tong Sampah yang Sesuai"),
gr.Image(label="Gambar Tong Sampah") # Display bin image
],
title="Klasifikasi Sampah dengan ResNet50 v1.2",
description="Unggah gambar sampah, dan model kami akan mengklasifikasikannya ke dalam salah satu dari 12 kategori bersama dengan warna tempat sampah yang sesuai. "
"Model ini bisa memprediksi jenis sampah dari ke-12 jenis berikut: Baterai, Sampah organik, Gelas Kaca Coklat, "
"Kardus, Pakaian, Gelas Kaca Hijau, Metal, Kertas, Plastik, Sepatu/sandal, Popok/pampers, Gelas Kaca bening,"
" NB: untuk masker, pampers disebut trash, tapi tong sampah masih sesuai "
)
iface.launch(share=True)