Slide 1

Slide 1 text

SSRͰಈతʹ 
 OGPը૾Λੜ੒͍ͨ͠ʂ 
 ʙCloud fl are Workers͔Β@vercel/ogҠߦฤʙ KFUG MEETUP @jiko21

Slide 2

Slide 2 text

About jiko21… Name: Daiki Kojima (jiko21) Multistack Engineer Love: Guitar, TypeScript @jiko21 @jiko_21

Slide 3

Slide 3 text

͜ΜͳτΠΞϓϦ࡞ͬͯ·͢ • Χϥʔίʔυͱ͔urlͰ؆୯ʹڞ༗Ͱ͖Δπʔϧ • OGը૾Ͱ։͔ͳͯ͘΋ͦͷ৔Ͱ৭͚ͩݟΕΔˣ

Slide 4

Slide 4 text

OGP

Slide 5

Slide 5 text

OGPΘ͔ΒΜͷͰChatGPTʹฉ͍ͯΈͨ

Slide 6

Slide 6 text

OGPΘ͔ΒΜͷͰChatGPTʹฉ͍ͯΈͨ

Slide 7

Slide 7 text

ͬͯॻ͍ͨΒऴΘΓʂ

Slide 8

Slide 8 text

ऴܶʂ

Slide 9

Slide 9 text

ಈతʹOGPը૾Λੜ੒ͯ͠షΓ͍ͨΜ΍ʂ • ͍ͭ΋ಉ͡ը૾͡Όͳͯ͘ • ϖʔδ • query parameter ɹͰOGPΛม͍͑ͨ

Slide 10

Slide 10 text

2020~2021ࠒͩͱ… • Cloud Functionsͱ͔Lambdaͱ͔ • ϝϦοτ • ࣮૷͸(ଟ෼)ָͦ͏ • σϝϦοτ • ॏͦ͏ (ͦΒͦ͏Α)

Slide 11

Slide 11 text

଎͍ͨ͘͠!!

Slide 12

Slide 12 text

଎͘͢Δʹ͸ • ίʔϧυελʔτͳ͍ํ͕خ͍͠! • ίʔϧυελʔτͪ͠Ό͏ͱͲ͏ͯ͠΋… • ͳΔ͚ͩϢʔβʔ͔Β͍ۙͱ͜ΖͰ • ౦ژϦʔδϣϯͱ͔͡Όͳͯ͘΋ͬͱۙ͘ʹ! 
 બ͹Εͨͷ͸&EHF8PSLFSͰͨ͠

Slide 13

Slide 13 text

Edge Worker΋Θ͔ΒΜͷͰChatGPTʹฉ͍ͯΈͨ

Slide 14

Slide 14 text

଎͘͢Δʹ͸(࠶ܝ) • ίʔϧυελʔτͳ͍ํ͕خ͍͠! • ίʔϧυελʔτͪ͠Ό͏ͱͲ͏ͯ͠΋… 
 㱺 (Cloud fl are workersͩͱ)ϗοτελʔτ • ͳΔ͚ͩϢʔβʔ͔Β͍ۙͱ͜ΖͰ • ౦ژϦʔδϣϯͱ͔͡Όͳͯ͘΋ͬͱۙ͘ʹ! 
 㱺·͞ʹͦ͏(CDNͳͷͰ)

Slide 15

Slide 15 text

cloud fl are workers

Slide 16

Slide 16 text

Cloud fl are WorkersͬͯԿ? • CDN࡞ͬͯΔCloud fl are͕΍ͬͯΔEdge WorkerͷαʔϏεج൫ • Nodeͱ͔Wasm͕Edge(CDN)্Ͱಈ͘ʂ • ҎԼ஫ҙ • NodeͷAPIͱ͔ݺͼग़ͤΔΘ͚͡Όͳ͍ • ϑΝΠϧαΠζʹ্ݶ(ѹॖޙͰධՁ͞ΕΔ͚Ͳ)͋Γ

Slide 17

Slide 17 text

Rust(Web AssemblyͰॻ͍ͨ fn get_params(text: String) -> Vec<[u8; 3]> { let mut rslt: Vec<[u8; 3]> = vec![]; let re = Regex::new(r"color=%23([0-9A-Fa-f] {6})").unwrap(); for mat in re.captures_iter(&text) { let rgb_string = mat.get(1).map_or("", |m| m.as_str()).trim().to_string(); let mut decoded = [0; 3]; hex::decode_to_slice(rgb_string, &mut decoded).expect("Decoding failed"); rslt.push(decoded) } rslt } fn gen_img(colors: &Vec<[u8; 3]>) -> Vec { let mut img: RgbImage = ImageBuffer::new(1200, 630); let color_size = colors.len() as u32; let each_size = 1200 / color_size; for (x, _y, pixel) in img.enumerate_pixels_mut() { let cursor = (x / each_size) as usize; *pixel = image::Rgb(*colors.get(cursor).unwrap()); } let mut img_bytes: Vec = Vec::new(); img.write_to(&mut Cursor::new(&mut img_bytes), image::ImageOutputFormat::Png).unwrap(); img_bytes } async fn hundle_ogp(colors: &Vec<[u8; 3]>) -> Result { let img_bytes = gen_img(colors); let mut resp = Response::from_bytes(img_bytes)?; resp.headers_mut().set("content-type", "image/png")?; Ok(resp) } #[event(fetch)] pub async fn main(req: Request, env: Env, _ctx: worker::Context) -> Result { utils::set_panic_hook(); let router = Router::new(); router .get_async("/", |req, _| async move { let url = req.url().unwrap(); if let Some(query_params) = req.url()?.query() { let params = query_params; hundle_ogp(&get_params(params.to_string())).await } else { let colors: Vec<[u8; 3]> = vec![[0, 0, 255], [0, 255, 0], [255, 255, 0], [239, 129, 15], [255, 0, 0]]; hundle_ogp(&colors).await } }) .run(req, env) .await }

Slide 18

Slide 18 text

࣮૷ͨ͠ࡶײ • Rustਏͬɺ • ͚Ͳ଎͍ • ͚ͲDocument͸͔ͳΓἧͬͯΔ • σϓϩΠ΍ςϯϓϨʔτ΋ἧͬͯΔ

Slide 19

Slide 19 text

࣮૷ͯ͠ 
 ͠͹Βͯ͘͠…

Slide 20

Slide 20 text

@vercel/og

Slide 21

Slide 21 text

@vercel/ogͬͯԿ? • VercelͷEdge Worker্Ͱಈ͘ը૾ੜ੒ϥΠϒϥϦ • ϝϦοτ • EdgeͰಈ͘ͷͰcoldstart΄΅ͳ͠ • HTML+CSSͰಈతʹը૾͕ੜ੒Ͱ͖ΔͷͰهड़ָ͕ʂ • Ωϟογϡͱ͔΋Α͠ͳʹ΍ͬͯ͘ΕΔ

Slide 22

Slide 22 text

@vercel/ogͰॻ͍ͨ export default function (req: NextRequest, res: NextResponse) { const paramColors = new URLSearchParams(req.nextUrl.search).getAll('color'); const colors = paramColors.length > 0 ? paramColors : ['#0000FF', '#00FF00', '#FFFF00', '#F0810F', '#FF0000'] return new ImageResponse( (
{colors.map((color) => (
))}
), { width: 1200, height: 630, }, ); } $44ࡶʹॻ͍ͨΒ 
 0(ੜ੒Ͱ͖Δͷ ͸Α͍

Slide 23

Slide 23 text

࣮૷ͨ͠ࡶײ • ָ • (VercelͰΞϓϦಈ͔͍ͯͨ͠Β)Vercel͚ͩͰ׬݁͢Δͷخ͍͠ • Vercel࠷ߴʂ

Slide 24

Slide 24 text

ͩͩ͠… • ຊ౰ʹύϑΥʔϚϯε͍͍ͷ͔? • Ωϟογϡͷ༗ແ΋ͦ͏͕ͩॳճͷੜ੒ίετͱ͔ • (ͳ͍͚Ͳ)େྔʹΞΫηεདྷͨͱ͖ͱ͔Ͳʔ͠Α

Slide 25

Slide 25 text

࣮ࡍʹݕূͯ͠ΈΔ

Slide 26

Slide 26 text

Ծઆ • RustͰbinaryΛ௚઀ੜ੒ͯ͠Δ͔Βੜ੒ࣗମ͸଎͍͸ͣ • @vercel/ogͩͱΩϟογϡ͸͏·͘࠷దԽ͞Ε͍ͯΔ͔Β2ճ໨Ҏ߱ ͷऔಘͱ͔͸଎͍͸ͣ

Slide 27

Slide 27 text

݁Ռ • ༧૝௨Γ(https://jiko21-tech-blog.monster/blog/2022-12-24/ cloud fl are-to-vecel-og) • ॳճ͸cloud fl are workers͕͸΍͍ • ͦΕҎ߱͸@vercel/og͕͸΍͍

Slide 28

Slide 28 text

Cloud fl are Workers΋ Cacheޮ͔ͤͨΒ͍͍ͷͰ͸ʁ

Slide 29

Slide 29 text

ͦΕ͸ͦ͏ɺͳΜ͚ͩͲ… • ݱ࣌఺ͰRustଆ(Wasm)ʹ͸cacheػೳ͕ͳ͍ • Durable ObjectsͳͲผ్ػೳͰؤுΔ͔͠ͳͦ͞͏ • ແཧ΍ΓલஈʹjsͰॻ͍ͨworkerΛڬΜ͚ͩͲ… • ͔֬ͩΊͩͬͨ…

Slide 30

Slide 30 text

݁࿦ • OGPը૾࡞Γ͍ͨͳΒNext.js+Vercelͷ૊Έ߹Θ͕ͤ࠷ڧ • ↑ແཧͳΒRustͰؤுΔͱ͍͏ͷ΋खͷ಺