✨(backend) add authenticated recording file access method
Implement secure recording file access through authentication instead of exposing S3 bucket or using temporary signed links with loose permissions. Inspired by docs and @spaccoud's implementation, with comprehensive viewset checks to prevent unauthorized recording downloads. The ingress reserved to media intercept the original request, and thanks to Nginx annotations, check with the backend if the user is allowed to donwload this recording file. This might introduce a dependency to Nginx in the project by the way. Note: Tests are integration-based rather than unit tests, requiring minio in the compose stack and CI environment. Implementation includes known botocore deprecation warnings that per GitHub issues won't be resolved for months.
This commit is contained in:
committed by
aleb_the_flash
parent
dc06b55693
commit
41c1f41ed2
@@ -11,7 +11,9 @@ from typing import Optional
|
||||
from uuid import uuid4
|
||||
|
||||
from django.conf import settings
|
||||
from django.core.files.storage import default_storage
|
||||
|
||||
import botocore
|
||||
from livekit.api import AccessToken, VideoGrants
|
||||
|
||||
|
||||
@@ -110,3 +112,33 @@ def generate_livekit_config(
|
||||
room=room_id, user=user, username=username, color=color
|
||||
),
|
||||
}
|
||||
|
||||
|
||||
def generate_s3_authorization_headers(key):
|
||||
"""
|
||||
Generate authorization headers for an s3 object.
|
||||
These headers can be used as an alternative to signed urls with many benefits:
|
||||
- the urls of our files never expire and can be stored in our recording' metadata
|
||||
- we don't leak authorized urls that could be shared (file access can only be done
|
||||
with cookies)
|
||||
- access control is truly realtime
|
||||
- the object storage service does not need to be exposed on internet
|
||||
"""
|
||||
|
||||
url = default_storage.unsigned_connection.meta.client.generate_presigned_url(
|
||||
"get_object",
|
||||
ExpiresIn=0,
|
||||
Params={"Bucket": default_storage.bucket_name, "Key": key},
|
||||
)
|
||||
|
||||
request = botocore.awsrequest.AWSRequest(method="get", url=url)
|
||||
|
||||
s3_client = default_storage.connection.meta.client
|
||||
# pylint: disable=protected-access
|
||||
credentials = s3_client._request_signer._credentials # noqa: SLF001
|
||||
frozen_credentials = credentials.get_frozen_credentials()
|
||||
region = s3_client.meta.region_name
|
||||
auth = botocore.auth.S3SigV4Auth(frozen_credentials, "s3", region)
|
||||
auth.add_auth(request)
|
||||
|
||||
return request
|
||||
|
||||
Reference in New Issue
Block a user