def download_asset(self, import_asset, redownload_asset): """ Download the URL specified for an Asset and save it to working storage """ if import_asset: item = import_asset.import_item.item download_url = import_asset.url asset = import_asset.asset elif redownload_asset: item = redownload_asset.item download_url = redownload_asset.download_url asset = redownload_asset else: logger.exception( "download_asset was called without an import asset or a redownload asset" ) raise asset_filename = os.path.join( item.project.campaign.slug, item.project.slug, item.item_id, "%d.jpg" % asset.sequence, ) try: # We'll download the remote file to a temporary file # and after that completes successfully will upload it # to the defined ASSET_STORAGE. with NamedTemporaryFile(mode="x+b") as temp_file: resp = requests.get(download_url, stream=True) resp.raise_for_status() for chunk in resp.iter_content(chunk_size=256 * 1024): temp_file.write(chunk) # Rewind the tempfile back to the first byte so we can temp_file.flush() temp_file.seek(0) ASSET_STORAGE.save(asset_filename, temp_file) except Exception: logger.exception("Unable to download %s to %s", download_url, asset_filename) raise
def download_asset(self, import_asset): """ Download the URL specified for an ImportItemAsset and save it to working storage """ item = import_asset.import_item.item asset_filename = os.path.join( item.project.campaign.slug, item.project.slug, item.item_id, "%d.jpg" % import_asset.sequence_number, ) try: # We'll download the remote file to a temporary file # and after that completes successfully will upload it # to the defined ASSET_STORAGE. with NamedTemporaryFile(mode="x+b") as temp_file: resp = requests.get(import_asset.url, stream=True) resp.raise_for_status() for chunk in resp.iter_content(chunk_size=256 * 1024): temp_file.write(chunk) # Rewind the tempfile back to the first byte so we can temp_file.flush() temp_file.seek(0) ASSET_STORAGE.save(asset_filename, temp_file) except Exception as exc: logger.error( "Unable to download %s to %s: %s", import_asset.url, asset_filename, exc, exc_info=True, ) raise
def get(self, request, *args, **kwargs): campaign = Campaign.objects.get(slug=self.kwargs["campaign_slug"]) asset_list = Asset.objects.filter(item__project__campaign=campaign).order_by( "title", "sequence" ) # FIXME: this code should be working in a separate path than the media root! # FIXME: we should be able to export at the project and item level, too export_base_dir = os.path.join(settings.MEDIA_ROOT, "exporter", campaign.slug) for asset in asset_list: src = os.path.join( settings.MEDIA_ROOT, asset.item.project.campaign.slug, asset.item.project.slug, asset.item.item_id, asset.slug, asset.media_url, ) dest_folder = os.path.join( export_base_dir, asset.item.project.slug, asset.item.item_id, asset.slug ) os.makedirs(dest_folder, exist_ok=True) dest = os.path.join(dest_folder, asset.media_url) if self.include_images: with open(dest, mode="wb") as dest_file: with ASSET_STORAGE.open(src, mode="rb") as src_file: for chunk in src_file.chunks(1048576): dest_file.write(chunk) # Get transcription data # FIXME: if we're not including all transcriptions, we should pick the completed or latest versions! try: transcription = Transcription.objects.get( asset=asset, user=self.request.user ).text except Transcription.DoesNotExist: transcription = "" # Build transcription output text file tran_output_path = os.path.join( dest_folder, "%s.txt" % os.path.basename(asset.media_url) ) with open(tran_output_path, "w") as f: f.write(transcription) # Turn Structure into bagit format bagit.make_bag(export_base_dir, {"Contact-Name": request.user.username}) # Build .zip file of bagit formatted Campaign Folder archive_name = export_base_dir shutil.make_archive(archive_name, "zip", export_base_dir) # Download zip with open("%s.zip" % export_base_dir, "rb") as zip_file: response = HttpResponse(zip_file, content_type="application/zip") response["Content-Disposition"] = "attachment; filename=%s.zip" % campaign.slug # Clean up temp folders & zipfile once exported shutil.rmtree(export_base_dir) os.remove("%s.zip" % export_base_dir) return response