Repository navigation
renderToString missing support for some SVG attributes #38553
Description
Description
For example, fillOpacity will convert to fillopacity instead of fill-opacity. Additionally, some attributes lose their case (e.g. preserveAspectRatio becomes preserveaspectratio) but that shouldn't cause issues outside validation.
Similar issues: #36903
Should there be a hardcoded list of exceptions?
Here's a list of SVG attributes React supports: https://reactjs.org/docs/dom-elements.html#all-supported-html-attributes
accentHeight accumulate additive alignmentBaseline allowReorder alphabetic
amplitude arabicForm ascent attributeName attributeType autoReverse azimuth
baseFrequency baseProfile baselineShift bbox begin bias by calcMode capHeight
clip clipPath clipPathUnits clipRule colorInterpolation
colorInterpolationFilters colorProfile colorRendering contentScriptType
contentStyleType cursor cx cy d decelerate descent diffuseConstant direction
display divisor dominantBaseline dur dx dy edgeMode elevation enableBackground
end exponent externalResourcesRequired fill fillOpacity fillRule filter
filterRes filterUnits floodColor floodOpacity focusable fontFamily fontSize
fontSizeAdjust fontStretch fontStyle fontVariant fontWeight format from fx fy
g1 g2 glyphName glyphOrientationHorizontal glyphOrientationVertical glyphRef
gradientTransform gradientUnits hanging horizAdvX horizOriginX ideographic
imageRendering in in2 intercept k k1 k2 k3 k4 kernelMatrix kernelUnitLength
kerning keyPoints keySplines keyTimes lengthAdjust letterSpacing lightingColor
limitingConeAngle local markerEnd markerHeight markerMid markerStart
markerUnits markerWidth mask maskContentUnits maskUnits mathematical mode
numOctaves offset opacity operator order orient orientation origin overflow
overlinePosition overlineThickness paintOrder panose1 pathLength
patternContentUnits patternTransform patternUnits pointerEvents points
pointsAtX pointsAtY pointsAtZ preserveAlpha preserveAspectRatio primitiveUnits
r radius refX refY renderingIntent repeatCount repeatDur requiredExtensions
requiredFeatures restart result rotate rx ry scale seed shapeRendering slope
spacing specularConstant specularExponent speed spreadMethod startOffset
stdDeviation stemh stemv stitchTiles stopColor stopOpacity
strikethroughPosition strikethroughThickness string stroke strokeDasharray
strokeDashoffset strokeLinecap strokeLinejoin strokeMiterlimit strokeOpacity
strokeWidth surfaceScale systemLanguage tableValues targetX targetY textAnchor
textDecoration textLength textRendering to transform u1 u2 underlinePosition
underlineThickness unicode unicodeBidi unicodeRange unitsPerEm vAlphabetic
vHanging vIdeographic vMathematical values vectorEffect version vertAdvY
vertOriginX vertOriginY viewBox viewTarget visibility widths wordSpacing
writingMode x x1 x2 xChannelSelector xHeight xlinkActuate xlinkArcrole
xlinkHref xlinkRole xlinkShow xlinkTitle xlinkType xmlns xmlnsXlink xmlBase
xmlLang xmlSpace y y1 y2 yChannelSelector z zoomAndPan
Step-by-step reproduction instructions
Run this:
import { renderToString } from '@wordpress/element'
const theString = renderToString(<svg><path fillOpacity={1}></path></svg>)
console.log(theString)Screenshots, screen recording, code snippet
Environment info
WP 5.9 and with and without the latest Gutenberg trunk build
Please confirm that you have searched existing issues in the repo.
Yes
Please confirm that you have tested with all plugins deactivated except Gutenberg.
Yes

Activity
KevinBatdorf commentedon Feb 6, 2022
Additionally, if I change an attribute in the block structure, Gutenberg will identify those changes as "corrupted" and report possible invalid content.
React's rendering on the right vs
renderToStringoutput on the left.gziolo commentedon Feb 11, 2022
Thank you for the report. We need to audit the mapping to ensure it is up to date with what React does in v17.
I closed that one as a duplicate. The case covered there was very specific so I think it makes sense to use this issue for tracking progress:
alshakerM commentedon Feb 20, 2022
I created a PR for this here: #38936. The list I added is the same list used in React main (trunk).
Thank you so much for the clear, elaborate issue @KevinBatdorf!
KevinBatdorf commentedon Feb 20, 2022
Hey @alshakerM looks good, but I think that PR only covers some of the issue, right? For example, would
preserveAspectRatiomaintain its case? Currently it changes topreserveaspectratio.viewBoxis another example.gziolo commentedon Feb 21, 2022
Thank you so much for starting this PR!
I see they have another file where they list all possible attributes:
https://github.com/facebook/react/blob/ca106a02d1648f4f0048b07c6b88f69aac175d3c/packages/react-dom/src/shared/possibleStandardNames.js
I'm wondering whether we should reuse more of their revised implementation to have the same handling for HTML attributes.
dgwyer commentedon Feb 23, 2022
Thanks for this PR!
I came across this today while trying to use
vectorEffectandstrokeWidthin the blocksave.jscomponent. They get converted tovectoreffectandstrokewidthwhich is obviously incorrect and breaks styling.gziolo commentedon Mar 1, 2022
This issue was fixed by @alshakerM in #38936. It should be available on npm next week after the Gutenberg v12.8 RC1 plugin release planned on Wednesday.
KevinBatdorf commentedon Mar 1, 2022
Nice work!