In this episode, we’ll explore how to enhance media management in your FastHTML app using advanced features of Cloudinary. You’ll learn how to apply image transformations, support video uploads, and implement tagging and search functionalities to manage your media effectively.
Part 1: Advanced Image Transformations with Cloudinary
Overview of Image Transformations:
Cloudinary provides powerful tools for transforming images directly via URL parameters. These transformations can optimize images for different devices, apply filters, resize, crop, and more, all dynamically without needing to store multiple versions of an image.
Step 1: Understanding Transformation URLs
Transformations in Cloudinary are applied by adding specific parameters to the URL of the image. For example, adding w_300,h_300,c_fill
will resize an image to 300×300 pixels and crop it to fill the dimensions.
Step 2: Applying Transformations in FastHTML
To use these transformations in your FastHTML app, modify your image gallery to include transformation parameters:
# main.py
from fasthtml.common import *
import config # Import Cloudinary configuration and functions
app, rt = fast_app()
@rt('/')
def get():
images = config.list_images()
image_elements = [
Img(
src=f"https://res.cloudinary.com/{config.cloudinary.config().cloud_name}/image/upload/w_300,h_300,c_fill/{img['public_id']}.jpg",
alt=img['public_id'],
cls='gallery-image',
onclick=f"openLightbox('https://res.cloudinary.com/{config.cloudinary.config().cloud_name}/image/upload/{img['public_id']}.jpg')"
) for img in images
]
return Div(
H1('Enhanced Image Gallery'),
Div(*image_elements, cls='gallery'),
Style('''
/* Add styles here */
'''),
Script('''
/* Add script here */
''')
)
serve()
Explanation of Code:
f"https://res.cloudinary.com/{config.cloudinary.config().cloud_name}/image/upload/w_300,h_300,c_fill/{img['public_id']}.jpg"
: Constructs the URL with transformation parameters to resize and crop images dynamically.onclick
attribute: Still uses the original image for the lightbox, which displays a larger version without transformation.
Step 3: Experiment with Different Transformations
Try different transformations like adding filters (e.g., e_sepia
for a sepia effect) or changing the image quality (q_auto
for automatic quality adjustment). Update your main.py
to see these changes.
Part 2: Adding Video Support to Your FastHTML App
Overview of Video Management in Cloudinary:
Cloudinary supports video uploads and transformations similar to images. You can upload videos, apply transformations, and deliver them efficiently.
Step 1: Update Upload Function for Video Support
Modify your upload
function in main.py
to handle video uploads:
@rt('/upload', methods=['POST'])
def upload(request):
try:
file = request.files['file']
if not file:
return Div(P('No file selected! Please choose a file to upload.'))
# Check file type for image or video
if file.content_type not in ['image/jpeg', 'image/png', 'image/gif', 'video/mp4', 'video/avi']:
return Div(P('Invalid file type! Please upload an image or video (JPEG, PNG, GIF, MP4, AVI).'))
# Upload file to Cloudinary
response = cloudinary.uploader.upload(file.file, resource_type="auto")
file_url = response['secure_url']
return Div(
P('File uploaded successfully!'),
A(file_url, 'View your file here', href=file_url, target='_blank')
)
except Exception as e:
return Div(P('An error occurred during upload: ' + str(e)))
Explanation of Code:
resource_type="auto"
: Automatically detects and handles the file type (image or video).- Support for Video File Types: Checks for both image and video file types to ensure only supported formats are uploaded.
Step 2: Display Videos in Your Gallery
Update your gallery to display videos alongside images:
@rt('/')
def get():
resources = config.list_images() # Use list_images or a modified function to list both images and videos
elements = []
for res in resources:
if res['resource_type'] == 'image':
elements.append(
Img(
src=f"https://res.cloudinary.com/{config.cloudinary.config().cloud_name}/image/upload/w_300,h_300,c_fill/{res['public_id']}.jpg",
alt=res['public_id'],
cls='gallery-image'
)
)
elif res['resource_type'] == 'video':
elements.append(
Video(
Src=f"https://res.cloudinary.com/{config.cloudinary.config().cloud_name}/video/upload/w_300,h_300,c_fill/{res['public_id']}.mp4",
controls=True,
cls='gallery-video'
)
)
return Div(
H1('Enhanced Media Gallery'),
Div(*elements, cls='gallery'),
Style('''
/* Add styles here */
''')
)
Explanation of Code:
Video(...)
: Adds video elements to the gallery with appropriate transformation URLs.- Conditional Logic: Checks if the resource type is an image or video to display accordingly.
Part 3: Implementing Tagging and Search Functionality
Overview of Tagging and Search:
Tagging allows you to categorize your media, making it easier to manage and retrieve specific files. Cloudinary supports tagging and searching media based on these tags.
Step 1: Tagging Images and Videos on Upload
Modify the upload
function to add tags:
@rt('/upload', methods=['POST'])
def upload(request):
try:
file = request.files['file']
tags = request.form.get('tags', '')
response = cloudinary.uploader.upload(file.file, resource_type="auto", tags=tags.split(','))
file_url = response['secure_url']
return Div(
P('File uploaded successfully!'),
A(file_url, 'View your file here', href=file_url, target='_blank')
)
except Exception as e:
return Div(P('An error occurred during upload: ' + str(e)))
Explanation of Code:
tags=tags.split(',')
: Takes tags from the form and splits them into a list for Cloudinary.
Step 2: Implement Search by Tag Functionality
Create a new route in main.py
to search images by tags:
@rt('/search', methods=['GET'])
def search(request):
tag = request.query.get('tag', '')
if not tag:
return Div(P('Please enter a tag to search.'))
resources = cloudinary.api.resources_by_tag(tag)
elements = [Img(src=res['secure_url'], alt=res['public_id'], cls='gallery-image') for res in resources.get('resources', [])]
return Div(
H1(f'Results for tag: {tag}'),
Div(*elements, cls='gallery'),
A('Back to gallery', href='/')
)
Explanation of Code:
request.query.get('tag', '')
: Retrieves the tag from the query parameters.cloudinary.api.resources_by_tag(tag)
: Fetches all media tagged with the specified tag.- Search Form: You can add a search form to the homepage to allow users to search by tag.
Conclusion
In this episode, you learned how to enhance your FastHTML app with advanced Cloudinary features like image transformations, video support, and tagging and search functionalities. These tools allow you to create a more dynamic and user-friendly media management system.
Homework/Assignment:
- Try adding more transformations, like rotation or adding watermarks to images.
- Enhance the search functionality to filter by multiple tags.
In the final episode, we will discuss how to deploy your FastHTML and Cloudinary-integrated application to a production environment!