Develop #16
@@ -371,7 +371,7 @@ async def upload_script(
|
|||||||
context: RequestContext = Depends(request_context),
|
context: RequestContext = Depends(request_context),
|
||||||
session: AsyncSession = Depends(database_session),
|
session: AsyncSession = Depends(database_session),
|
||||||
) -> dict[str, Any]:
|
) -> dict[str, Any]:
|
||||||
suffix = Path(file_name).suffix.lower()
|
suffix = PurePosixPath(file_name).suffix.lower()
|
||||||
if suffix not in {".py", ".ipynb"}:
|
if suffix not in {".py", ".ipynb"}:
|
||||||
raise HTTPException(
|
raise HTTPException(
|
||||||
status.HTTP_422_UNPROCESSABLE_ENTITY,
|
status.HTTP_422_UNPROCESSABLE_ENTITY,
|
||||||
@@ -637,6 +637,7 @@ async def update_script(
|
|||||||
status.HTTP_409_CONFLICT,
|
status.HTTP_409_CONFLICT,
|
||||||
"script has no workspace path",
|
"script has no workspace path",
|
||||||
)
|
)
|
||||||
|
old_object_id = script.current_object_id
|
||||||
storage_data = await request.app.state.storage_client.create_server_object(
|
storage_data = await request.app.state.storage_client.create_server_object(
|
||||||
workspace_id=context.workspace.workspace_id,
|
workspace_id=context.workspace.workspace_id,
|
||||||
user_id=script.owner_user_id,
|
user_id=script.owner_user_id,
|
||||||
@@ -653,12 +654,16 @@ async def update_script(
|
|||||||
f"{hashlib.sha256(content).hexdigest()}"
|
f"{hashlib.sha256(content).hexdigest()}"
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
storage_object.content_hash = storage_data["content_hash"]
|
script.current_object_id = storage_data["storage_object_id"]
|
||||||
storage_object.size_bytes = storage_data["size_bytes"]
|
|
||||||
script.updated_at = datetime.now(UTC).replace(tzinfo=None)
|
script.updated_at = datetime.now(UTC).replace(tzinfo=None)
|
||||||
|
if old_object_id != script.current_object_id:
|
||||||
|
try:
|
||||||
|
await request.app.state.storage_client.delete_object(old_object_id)
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
return {
|
return {
|
||||||
"request_id": context.request_id,
|
"request_id": context.request_id,
|
||||||
"data": script_payload(script, storage_object),
|
"data": script_payload(script, storage_data),
|
||||||
"meta": {},
|
"meta": {},
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -738,18 +743,11 @@ async def publish_version(
|
|||||||
"script working copy is not stored in object storage",
|
"script working copy is not stored in object storage",
|
||||||
)
|
)
|
||||||
|
|
||||||
def read_object_bytes() -> bytes:
|
content = await asyncio.to_thread(
|
||||||
response = request.app.state.object_store.get_object(
|
request.app.state.object_store.get_bytes,
|
||||||
Bucket=source_object.bucket_name,
|
bucket_name=source_object.bucket_name,
|
||||||
Key=source_object.object_key,
|
object_key=source_object.object_key,
|
||||||
)
|
)
|
||||||
body = response["Body"]
|
|
||||||
try:
|
|
||||||
return body.read()
|
|
||||||
finally:
|
|
||||||
body.close()
|
|
||||||
|
|
||||||
content = await asyncio.to_thread(read_object_bytes)
|
|
||||||
content_hash = hashlib.sha256(content).hexdigest()
|
content_hash = hashlib.sha256(content).hexdigest()
|
||||||
existing = await session.scalar(
|
existing = await session.scalar(
|
||||||
select(Versions).where(
|
select(Versions).where(
|
||||||
|
|||||||
@@ -366,7 +366,7 @@ async def complete_upload_record(
|
|||||||
object_key_hash=upload.object_key_hash,
|
object_key_hash=upload.object_key_hash,
|
||||||
storage_uri=f"s3://{upload.bucket_name}/{upload.object_key}",
|
storage_uri=f"s3://{upload.bucket_name}/{upload.object_key}",
|
||||||
file_name=file_name,
|
file_name=file_name,
|
||||||
file_extension=Path(file_name).suffix.lower() or None,
|
file_extension=PurePosixPath(file_name).suffix.lower() or None,
|
||||||
mime_type=actual_content_type,
|
mime_type=actual_content_type,
|
||||||
size_bytes=actual_size,
|
size_bytes=actual_size,
|
||||||
content_hash=actual_hash,
|
content_hash=actual_hash,
|
||||||
|
|||||||
@@ -137,6 +137,14 @@ class RustFSObjectStore:
|
|||||||
def head(self, *, bucket_name: str, object_key: str) -> dict[str, Any]:
|
def head(self, *, bucket_name: str, object_key: str) -> dict[str, Any]:
|
||||||
return self.internal.head_object(Bucket=bucket_name, Key=object_key)
|
return self.internal.head_object(Bucket=bucket_name, Key=object_key)
|
||||||
|
|
||||||
|
def get_bytes(self, *, bucket_name: str, object_key: str) -> bytes:
|
||||||
|
response = self.internal.get_object(Bucket=bucket_name, Key=object_key)
|
||||||
|
body: BinaryIO = response["Body"]
|
||||||
|
try:
|
||||||
|
return body.read()
|
||||||
|
finally:
|
||||||
|
body.close()
|
||||||
|
|
||||||
def sha256(self, *, bucket_name: str, object_key: str) -> str:
|
def sha256(self, *, bucket_name: str, object_key: str) -> str:
|
||||||
response = self.internal.get_object(Bucket=bucket_name, Key=object_key)
|
response = self.internal.get_object(Bucket=bucket_name, Key=object_key)
|
||||||
body: BinaryIO = response["Body"]
|
body: BinaryIO = response["Body"]
|
||||||
|
|||||||
Reference in New Issue
Block a user