quartz icon indicating copy to clipboard operation
quartz copied to clipboard

feat(open-graph): Add ability to generate OG images + further OG support

Open benschlegel opened this issue 1 year ago • 27 comments

After finally getting around to writing the docs, the open graph PR is now ready for review.

A detailed overview over how this works can be found in the docs now, but in summary, this enables users to automatically generate OG images with a lot of customisation options (even the ability to provide your own html/css satori component via config!)

image

This uses satori to generate an svg from html/css markup and sharp to convert it to .webp with some additional compression.

As discussed, this feature is disabled by default (so is opt-in). I only have figures from 4 months ago when I implemented this PR, but the total file size for all images for the entire docs folder was just 960KB, with an average of around 19KB per image.

This PR also adds some further Open Graph configuration support by adding frontmatter properties to override description/image (with aliases to support the matching ones from obsidian publish).

If you have any questions, improvements or remarks, please let me know :)

benschlegel avatar Jan 27 '24 22:01 benschlegel

small ask. Can you rebase this onto main so that it would only be one commit 😄 Probably a bit easier to cherry-pick and test out the changes :)

aarnphm avatar Jan 28 '24 04:01 aarnphm

small ask. Can you rebase this onto main so that it would only be one commit 😄 Probably a bit easier to cherry-pick and test out the changes :)

its ok, all PRs are squashed before merging anyways :)

jackyzha0 avatar Jan 28 '24 06:01 jackyzha0

small design nit before i look at this further, can we get a layout more like this?

image

jackyzha0 avatar Jan 28 '24 07:01 jackyzha0

Sure, will change the default layout :)

Few questions about how you want this implemented

What about the logo? Should this use the icon.png from the static folder? (could use to some funky looks if users have icons that differ greatly in size/aspect ratio). Or should this always use the quartz icon statically? Should users then also be able to further customise what icon is used here, or is relying on the site icon fine

The font size for the header size seems pretty big, from my testing, this was already pretty hard to fit with longer titles. How do you want to handle cases for long titles? Right now, I have a "breakpoint" variable, and if the title exceeds that length, it gets turned into a smaller font size. Alternatively, we could multi-line the title (tho that could look weird quickly next to the icon) or cut off the title with "..." if it gets too long.

benschlegel avatar Jan 28 '24 08:01 benschlegel

Little suggestion: allow to change the default image path for frontmatter, so I can use content/img instead.

Mara-Li avatar Jan 28 '24 08:01 Mara-Li

Little suggestion: allow to change the default image path for frontmatter, so I can use content/img instead.

Def something that can be improved in the future, but probably better to change this in a separate PR, as this one already has over 1000 line changes and is a lot to review at once (for sure want to add something this tho, alongside the ability to add external urls for images :) )

benschlegel avatar Jan 28 '24 09:01 benschlegel

Little suggestion: allow to change the default image path for frontmatter, so I can use content/img instead.

Def something that can be improved in the future, but probably better to change this in a separate PR, as this one already has over 1000 line changes and is a lot to review at once (for sure want to add something this tho, alongside the ability to add external urls for images :) )

No problem, i will wait for the approvable and make an additional update right after!

Mara-Li avatar Jan 28 '24 09:01 Mara-Li

Little suggestion: allow to change the default image path for frontmatter, so I can use content/img instead.

For this particular feature, we should use the same as Obsidian : https://help.obsidian.md/Obsidian+Publish/Social+media+link+previews#Image

lucastucious avatar Jan 29 '24 10:01 lucastucious

Sure, will change the default layout :)

Few questions about how you want this implemented

What about the logo? Should this use the icon.png from the static folder? (could use to some funky looks if users have icons that differ greatly in size/aspect ratio). Or should this always use the quartz icon statically? Should users then also be able to further customise what icon is used here, or is relying on the site icon fine

The font size for the header size seems pretty big, from my testing, this was already pretty hard to fit with longer titles. How do you want to handle cases for long titles? Right now, I have a "breakpoint" variable, and if the title exceeds that length, it gets turned into a smaller font size. Alternatively, we could multi-line the title (tho that could look weird quickly next to the icon) or cut off the title with "..." if it gets too long.

  • Let's try to use icon.png, this is the favicon anyways so safe to assume it is close to 1:1
  • Breakpoint seams reasonable :)

jackyzha0 avatar Jan 31 '24 06:01 jackyzha0

Could you rebase to fix the merge conflict?

jackyzha0 avatar Jan 31 '24 06:01 jackyzha0

I'll take a look at changing the default image, fix the merge issues and address your review today or tmrw hopefully :)

benschlegel avatar Jan 31 '24 17:01 benschlegel

image Should we name these based on slugs instead of path?

Oh and also space also needs to be escape afaik

aarnphm avatar Feb 06 '24 09:02 aarnphm

image Should we name these based on slugs instead of path?

Oh and also space also needs to be escape afaik

I don't think slugs have to be globally unique, so using slugs doesn't really provide a benefit and would just require an additional step of making sure every file name is unique. By using paths, the OS already guarantees uniqueness if we take the full path.

For spaces, do we need to escape them? On windows and mac it works just fine, not sure if there are some Linux distributions that can't handle spaces in file names.

Still haven't gotten around to fixing everything from the review up bc i got sick, but hopefully soon now :)

benschlegel avatar Feb 06 '24 10:02 benschlegel

no worries wish you a speedy recovery! let us know if there is anything we can help with.

aarnphm avatar Feb 06 '24 10:02 aarnphm

@benschlegel any updates on this PR?

aarnphm avatar Feb 22 '24 14:02 aarnphm

been some really stressful weeks, i probably have a few hours tomorrow to take a look and then some more starting next wednesday, just fyi but hopefully finally get some free time to take a look

benschlegel avatar Feb 22 '24 15:02 benschlegel

We will have to decide whether we want to generate this on demand or dump everything pre-serving time.

pre-serve will cost cold start a bunch, reload with this one is essentially 30s every reload trigger ( for a 200 files vault, can't imagine for vault that is 5k+)

I think probably best if the components is async, then it would help creating this on demand (which is probably better)

current solution:

      if (cfg.generateSocialImages && !ctx.argv.serve) {}

aarnphm avatar Feb 23 '24 21:02 aarnphm

Really excited for this one! Appreciate the effort, guys 🙌

strombraaten avatar Feb 25 '24 22:02 strombraaten

We will have to decide whether we want to generate this on demand or dump everything pre-serving time.

pre-serve will cost cold start a bunch, reload with this one is essentially 30s every reload trigger ( for a 200 files vault, can't imagine for vault that is 5k+)

I think probably best if the components is async, then it would help creating this on demand (which is probably better)

current solution:

      if (cfg.generateSocialImages && !ctx.argv.serve) {}

This is an area that can be improved for sure, currently, all images are generated on startup (but async, so it doesn't block). Maybe this is an improvement that could be made in a future PR, as it's already hard to keep track of every review here (and i still have a lot to go through from jacky). Since this feature is disabled by default anyways, I don't think this is too critical for now. I know I personally don't have enough free time atm to test out your proposed changes in context of all possible config options and other quartz config, but if you do and it all still works as expected, we can also add this now

benschlegel avatar Mar 07 '24 18:03 benschlegel

I think this has to do with us cleanup the public files everytime for hot reload, which means each hot reload will recreate the webp everytime.

I don't know if async helps or do anything here.

Also I think my comments previously is probably because I move the image generation to componentResources.ts, hence the blocking.

aarnphm avatar Mar 08 '24 04:03 aarnphm

hi @benschlegel, sorry for the ping, if you still want to work on the PR lmk, or I can help with continuing your work here.

aarnphm avatar Jul 10 '24 04:07 aarnphm

hi @benschlegel, sorry for the ping, if you still want to work on the PR lmk, or I can help with continuing your work here.

Hey, no worries. Uni has been going crazy and I didn't really have time to work on this until now, but semester is over now and I should get some time again soon. If you need this sooner or want to do it yourself, that works too, but I don't think too much is missing to get this finished now.

benschlegel avatar Jul 11 '24 08:07 benschlegel

no worries at all really. I have implemented this on my side, this is rather bringing this to Quartz.

aarnphm avatar Jul 12 '24 00:07 aarnphm

This would be such a killer feature. Thanks for putting the work in! ❤️

Keyruu avatar Jul 22 '24 21:07 Keyruu