Coder Social home page Coder Social logo

andreipfeiffer / css-in-js Goto Github PK

View Code? Open in Web Editor NEW
811.0 15.0 23.0 1.98 MB

A thorough analysis of all the current CSS-in-JS solutions with SSR & TypeScript support for Next.js

CSS 43.91% TypeScript 56.09%
css-in-js typescript reactjs nextjs styling comparison

css-in-js's People

Contributors

andreipfeiffer avatar hotell avatar karlhorky avatar layershifter avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

css-in-js's Issues

Question - dynamic styles from DB in SSR or React Server Components

Hello! Great research. After reading this research I think you might be able to solve our weird use case!

We store our styles in the database and we use nextjs. I'm looking for something that could run the fetch in the server side and inyect the styles with automatic hydration.

Using runtime librarie like twind or the runtime version of unoCss kinda works, but generates extra loading time as everything is done in the client side.

Thanks!

Include TailwindCSS?

Not strictly CSS but I would love to see it compared with the rest. Have you considered including it?

Feedback round

Resulting from our conversation on Twitter, here is my Feedback. https://twitter.com/pfeiffer_andrei/status/1357304032059080704?s=20, this feedback mostly concerns with the common things across all libs and specific things for JSS. I haven't read all the specific info about other libs.

Hope this helps to improve the document. I am sorry if anything sounds offensive. This is meant to be a constructive critique and as usual, on the internet, it's hard to convey a critique without offending.

DX: Developer eXperience which includes:

syntax highlighting

I am guessing you are talking about CSS specific syntax highlighting here, which is not clearly explained there. It seems you set on green the libraries that have template strings syntax support and have vscode plugins for syntax highlighting. The same libraries support object-based syntax and I am guessing they won't have syntax highlighting if you use it.

It needs to be clear that is basically saying there will be syntax highlighting when using template strings.
As a side note, JSS has an optional plugin for template strings, I am guessing syntax highlighting tools react on css``, so if one really wanted they could write a one-liner CSS tag that just returns the same string for JSS and it would highlight. I agree though if this doesn't come out of the box, people might not know they can do it. Maybe this should be added.

code-completion for CSS properties and values

Here it's not clear what type of completion you are talking about. Is it based on typedefs or emmet, something else?
If you are talking about types based completion, there is a big difference between validating valid property names, existing CSS values OR it actually does completely check if a property X can be used with a value Y.

You will find a large discrepancy between different libraries, typescript, flowtype, and the 3 above named levels of guarantees.

tag

As I already mentioned JSS provides it through an optional plugin, in a limited/minimal capacity. I find parsing CSS with JS in runtime is a bad idea if it's not done at build time. I am not sure this should go as a pure benefit, where it has bundle and runtime cost.

{ }: support for defining styles as objects

"more suitable for new projects, when you don't need to migrate existing CSS"

This is not true, you can start using it at any point in time and migrate one component after another. If you need to reuse a CSS rule in the legacy part and in the new part at the same time during the migration period, you either make sure the rule is encapsulated inside a component and the same component is reused or you reuse it by composing globally scoped rules and local once in the new parts. For example, JSS offers composition plugin, or you can add a second class to the element directly and there are some more ways to achieve that.

without TS support, you won't get code completion

Or flowtype

TS

JSS has TS defs built-in, I am not sure how good they are since I am not personally maintaining them, but they are definitely there.

& ctx

In the case of JSS, I don't know why it says it's partial support, JSS had this syntax from day 1.

Nesting

In the case of JSS, I don't know why it says it's partial support, JSS had this syntax from day 1.

Thoughts on bundle size

It's hard to compare bundle size when a library is composed of plugins and they are all optional like it is in the case of JSS.
Because of plugins architecture, there are also different features, for e.g. JSS core is 6.6kB according to bundlephobia. What you mention in the table is react-jss, which contains some features other libraries don't have. It bundles the default preset package, which bundles most official plugins with an exception of a few.

I am not sure which specific packages you have been using to get the bundle size data in case of all the other libs. This should be made somehow very clear, e.g. emotion is pretty much a collection of packages.

Global styles

"JSS has a convoluted API for this, which requires an additional plugin, which we didn't figure out how to implement"

I have no idea why you say it because the API itself is straight forward and the plugin is part of the default preset, which is part of react-jss package I assume you have been trying. So all it should take is to use the syntax, essentially the same syntax as the rest of it, but inside of a @global rule, so keys become global selectors instead of rule names with generated selectors.

Vendor prefixes

"JSS requires an additional plugin for this"

Again if you tested react-jss, it's already part of it, since it's in the default preset.

Unique class names

Actually, there is a big difference in algorithms used for that. Different hashing methods vs. counters based like JSS does it.

No inline styles

" pioneers like Radium & Glamor. " neither of them are pioneers in cssinjs and only Radium uses a hybrid approach with inline .styles

FCP

For solutions that don't support .css file extraction, SSRed styles are added as <style> tags in the <head>, which will result in higher FCP than using regular CSS, because .css files can and will be loaded in parallel to other resources, while big <style> content will be sent and parsed along with the HTML, increasing parsing time.

Honestly, this is entirely wrong and I don't know where this misinformation comes from, sorry.

Critical CSS in the head are designed SPECIFICALLY to improve FCP. It allows the document to not have a render-blocking link tag with CSS in the head and start to render the contents as the HTML document arrives with correct styles.
If you have a gigantic page and your critical CSS is the reason why the document is too slow before there is first contentful paint, you will have an even bigger problem with an extracted blocking CSS file when a user comes with an empty cache.

Debugging / Inspecting

Most solutions inject the <style> tag in the DOM in DEVELOPMENT, which is a slower approach, but enables style inspecting using browser dev tools. But when building for PRODUCTION, they use CSSStyleSheet.insertRule() to inject the styles directly into the CSSOM, which is a way faster approach, but you cannot inspect the styles.

    JSS and Stitches use insertRule() in dev mode as well, so you cannot see what gets injected
    TypeStyle does NOT use insertRule(), not even in production

Most solutions inject the <style> tag in the DOM in DEVELOPMENT, which is a slower approach,

Slower approach than what, link tag with a CSS file? Slower how/why?

but enables style inspecting using browser dev tools

No, this is not what enables dev tools. There are a number of apis to render styles inside of style tag, style.textContent, style.innerHTML, style.appednChild(textNode) and finally style.sheet.insertRule()

JSS and Stitches use insertRule() in dev mode as well, so you cannot see what gets injected

JSS uses a hybrid approach, static styles are inserted using .textContent, dynamic once (function values) using insertRule

I believe emotion and styled components also use insertRule, maybe not always, needs verification

which is a way faster approach, but you cannot inspect the styles.

No. Actually insertRule is slower than textContent, but marginally. What makes .textContent slow is the fact that you can't add rules, when you set .textÇontent it sets the entire CSS string and the browser has to parse this entire string.

A one-of render with .textContent of a larger amount of CSS rules will be significantly faster than the same rules inserted using insertRule.

but you cannot inspect the styles.

This is not true. What you can't do is see the styles in style element in elements tab in dev tools.
What you always could do is to see the styles in the styles panel in dev tools and it was always pointing to the style element they come from if you wanted to see it. In addition to that, you can always go into object inspector of the style element, open style.sheet.cssRules and see all the rules there.

The actual problem browsers had for no reason is that you couldn't EDIT the style rules inserted using insertRule API, you could always overwrite them with inline styles if you needed to try something out, in the same style tab, just couldn't edit the CSS rule itself.

This has changed a few months ago in chrome dev tools btw. You still can't see the styles in elements inspector but that's a spec design, insertRule is a CSSOM API, elements inspector works with the DOM API. When you use insertRule, you don't generate a DOM representation for those styles, it goes directly into CSSOM.

For example style.textContent is a DOM API that interacts with CSSOM internally and creates the CSS rules AND the dom string representation, so when this one is used, you can see CSS in the elements tab inside style element.

Launched in 2016

Actually no, its launched in 2014

Add theming details

  • Example of using theming
  • Different approaches to how it is achieved: CSS vars, JS Context passing, etc

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.