def test_image_with_scale_time(self): metadata = converters.parse_path("*****@*****.**") self.assertEqual(metadata["title"], "Album Art") self.assertEqual(metadata["date"], datetime.datetime(2014, 2, 21, 18, 24)) self.assertEqual(metadata["url"], "/2014-02-21-18-24-album-art@2x/") self.assertEqual(metadata["scale"], 2)
def render(self, context, path, caller): if not path.startswith("/"): path = context["page"]["url"] + path url = converters.parse_path(path)['url'] template = self.environment.get_template("extensions/video.html") return template.render(site=self.environment.site, video=self.environment.store.get(url))
def test_post_index_no_date(self): metadata = converters.parse_path( "/posts/this-is-a-post/index.markdown") self.assertEqual(metadata["title"], "This Is a Post") self.assertFalse("date" in metadata) self.assertEqual(metadata["url"], "/posts/this-is-a-post/") self.assertEqual(metadata["parent"], "/posts/")
def test_time_no_title(self): metadata = converters.parse_path( "photos/instagram/2016-03-09-17-48-00.jpg") self.assertFalse("title" in metadata) self.assertEqual(metadata["date"], datetime.datetime(2016, 3, 9, 17, 48, 00)) self.assertEqual(metadata["url"], "/photos/instagram/2016-03-09-17-48-00/")
def test_post_index_date(self): metadata = converters.parse_path( "/posts/2017-12-11-this-is-a-post/index.markdown") self.assertEqual(metadata["title"], "This Is a Post") self.assertEqual(metadata["date"], datetime.datetime(2017, 12, 11, 0, 0)) self.assertEqual(metadata["url"], "/posts/2017-12-11-this-is-a-post/") self.assertEqual(metadata["parent"], "/posts/")
def process_image(incontext, root, destination, dirname, basename, category, title_from_filename=True): source_path = os.path.join(root, dirname, basename) identifier = generate_identifier(basename) destination_dir = os.path.join(destination, dirname) destination_path = os.path.join(destination_dir, basename) markdown_path = os.path.join(destination_dir, "%s.markdown" % identifier) name, ext = os.path.splitext(basename) utils.makedirs(destination_dir) metadata = load_metadata(markdown_path) DEFAULT_PROFILES = { "image": { "width": 1600, "scale": 1 }, "thumbnail": { "height": 240, "scale": 2 }, } EQUIRECTANGULAR_PROFILES = { "image": { "width": 10000, "scale": 1 }, "thumbnail": { "height": 240, "scale": 2 }, } # Use the common path parsing from converters to ensure we pick up information like the title, etc. metadata = converters.parse_path(os.path.join(dirname, basename), title_from_filename=title_from_filename) # Read data from the EXIF and add it to the metadata exif_data = exif(source_path) # Select title with priority: Title, ObjectName if "ObjectName" in exif_data: metadata["title"] = exif_data["ObjectName"] if "Title" in exif_data: metadata["title"] = exif_data["Title"] metadata["content"] = first_value_or_none( exif_data, ["ImageDescription", "Description", "ArtworkContentDescription"]) if "DateTimeOriginal" in exif_data: metadata["date"] = exif_data["DateTimeOriginal"] if "ProjectionType" in exif_data: metadata["projection"] = exif_data["ProjectionType"] logging.debug(f"projection = {metadata['projection']}") # Read the location from the exif. if "GPSLatitude" in exif_data and "GPSLongitude" in exif_data: metadata["location"] = { "latitude": exif_data["GPSLatitude"], "longitude": exif_data["GPSLongitude"] } # Determine which profiles to use; we use a different profile for equirectangular projections. # TODO: In an ideal world we would allow all of this special case behaviour to be configured in site.yaml # so there are no custom modifications required to the script. profiles = DEFAULT_PROFILES if "projection" in metadata and metadata["projection"] == "equirectangular": profiles = EQUIRECTANGULAR_PROFILES # Generate the various different image sizes. # TODO: Consider making this common code for all images. for profile_name, profile_details in profiles.items(): filename = "%s-%s%s" % (identifier, profile_name.replace("_", "-"), ext) if profile_name == "image": filename = "%s%s" % (identifier, ext) scale = 1 if "scale" in profile_details: scale = profile_details["scale"] width = None if "width" in profile_details: width = profile_details["width"] height = None if "height" in profile_details: height = profile_details["height"] source_scale = metadata["scale"] if metadata["scale"] is not None else 1 # TODO: Rename generate_thumbnail. metadata[profile_name] = generate_thumbnail(source_path, destination, dirname, filename, (width, height), source_scale, scale) # Configure the page details. metadata["category"] = category metadata["template"] = "photo.html" # TODO: Pass this in as a default. metadata["path"] = converters.ensure_leading_slash( os.path.join(dirname, basename)) metadata_document = store.Document(metadata['url'], metadata, os.path.getmtime(source_path)) incontext.environment["DOCUMENT_STORE"].add(metadata_document) files = [markdown_path] + [ os.path.join(destination, dirname, metadata[f]["filename"]) for f in profiles.keys() ] files = [ os.path.join(destination, dirname, metadata[f]["filename"]) for f in profiles.keys() ] return {'files': files, 'urls': [metadata['url']]}
def test_post_titlecase_with_number(self): metadata = converters.parse_path( "2016-10-24-vision-of-the-future-2000.markdown") self.assertEqual(metadata["title"], "Vision of the Future 2000")
def inner(path): root, dirname, basename = utils.tripple(from_directory, path) destination = os.path.join(to_directory, dirname, basename) utils.makedirs(os.path.join(to_directory, dirname)) data = converters.parse_path(os.path.join(dirname, basename), title_from_filename=title_from_filename) data['content'] = '' data["category"] = category data[ "template"] = "photo.html" # TODO: Change this to be part of the configuration. exif = gallery.exif(path) if "Title" in exif: data["title"] = exif["Title"] if "Description" in exif: data["content"] = exif["Description"] if "ImageDescription" in exif: data["content"] = exif["ImageDescription"] if "CreationDate" in exif: data["date"] = exif["CreationDate"] if "ContentCreateDate" in exif: data["date"] = exif["ContentCreateDate"] name, _ = os.path.splitext(basename) mp4_name = "%s.mp4" % name mp4_path = os.path.join(to_directory, dirname, mp4_name) if not os.path.exists(mp4_path): subprocess.check_call([ "ffmpeg", "-y", "-i", path, "-vcodec", "h264", "-acodec", "aac", "-strict", "-2", "-vf", "scale=1080:trunc(ow/a/2)*2", "-loglevel", LOG_LEVEL_PANIC, mp4_path ]) thumbnail_name = "%s-thumbnail.jpg" % name thumbnail_path = os.path.join(to_directory, dirname, thumbnail_name) if not os.path.exists(thumbnail_path): subprocess.check_call([ "ffmpeg", "-y", "-i", path, "-ss", "00:00:1.000", "-vframes", "1", "-loglevel", LOG_LEVEL_PANIC, thumbnail_path ]) size = gallery.get_size(thumbnail_path, 1) data["thumbnail"] = converters.merge_dictionaries( { 'filename': thumbnail_name, 'url': os.path.join("/", dirname, thumbnail_name) }, size) data["video"] = converters.merge_dictionaries( { 'filename': mp4_name, 'url': os.path.join("/", dirname, mp4_name) }, size) data["path"] = converters.ensure_leading_slash(path) document = store.Document(data["url"], data, os.path.getmtime(path)) incontext.environment["DOCUMENT_STORE"].add(document) return {'files': [mp4_path, thumbnail_path], 'urls': [document.url]}
def metadata_for_media_file(root, path, title_from_filename): metadata = converters.parse_path(path, title_from_filename=title_from_filename) exif_metadata = metadata_from_exif(os.path.join(root, path)) metadata = utils.merge_dictionaries(metadata, exif_metadata) return metadata