Skip to content

Instantly share code, notes, and snippets.

@Ambi93
Forked from ll14m4n/yt_video_url.md.txt
Created February 18, 2025 04:12
Show Gist options
  • Select an option

  • Save Ambi93/4bb7b171f6fa6d6c411f25189242bab0 to your computer and use it in GitHub Desktop.

Select an option

Save Ambi93/4bb7b171f6fa6d6c411f25189242bab0 to your computer and use it in GitHub Desktop.
obsidian youtube templater
<%*
/*
You need to install yt-dlp and jq to use this template:
$ brew install yt-dlp jq # on macOS
You need to define user function in Templater plugin settings named "ytmeta" with the following command:
/opt/homebrew/yt-dlp -j "https://www.youtube.com/watch?v=${id}" | /opt/homebrew/jq "${query}"
replace /opt/homebrew with your path to yt-dlp and jq
*/
const query = "{title: .title, thumbnail: .thumbnail, duration_seconds: .duration, upload_date: .upload_date, description: .description, chapters: .chapters, channel_name: .channel, uploader_id: .uploader_id}"
format_duration = (duration_seconds) => {
const duration_ms = duration_seconds * 1000
duration_h = Math.floor(moment.duration(duration_ms).asHours()) || ""
duration_m_s = moment.utc(duration_ms).format("mm:ss")
return [duration_h, duration_m_s].filter(Boolean).join(":")
}
clean_obsidian_link = (name) => {
const filename_forbid_chars = /[*\/\\<>:|?"']/g
return name.replace(filename_forbid_chars, '_')
}
const url_input = await tp.system.prompt("Video URL")
const u = new URL(url_input);
const video_id = u.searchParams.get("v")
const meta_resp = await tp.user.ytmeta( { id: video_id, query: query } )
const meta = JSON.parse(meta_resp)
const title = meta.title
const thumbnail = meta.thumbnail
const duration = format_duration(meta.duration_seconds)
const ud = meta.upload_date
const upload_date = ud.slice(0, 4) + '-' + ud.slice(4, 6) + '-' + ud.slice(6, 8);
const description = meta.description
const canonical_url = `https://www.youtube.com/watch?v=${video_id}`
const filename = clean_obsidian_link('📺 ' + title)
const chapters_ar = meta.chapters || []
let chapters = ''
let notes = "## Notes\n"
if (chapters_ar.length > 0) {
chapters += chapters_ar.map((c) => {
const start = format_duration(c.start_time)
return `- [${c.title} (${start})](${canonical_url}&t=${c.start_time})`
}).join("\n")
notes += chapters_ar.map((c) => {
const start = format_duration(c.start_time)
return `### ${c.title}\n[(${start})](<${canonical_url}&t=${c.start_time}>)\n`
}).join("\n")
}
await tp.file.rename(filename)
tR += `---
tag: source/📺vid
id: "${video_id}"
channel: "[[${meta.uploader_id}]]"
title: "${title}"
duration: ${duration}
publish_date: ${upload_date}
url: ${canonical_url}
up:
---
![Thumbnail](${thumbnail})
[Watch (${duration})](${canonical_url})
${chapters}
## Description
\`\`\`
${description}
\`\`\`
${notes}
`
%>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment