Closed xxn520 closed 4 years ago
styled components:0.4.4
?
这个版本是不是太老了?
提供一个可复现仓库吧
4.4.0,5 以上也能复现。
仓库弄一个比较麻烦,晚点提供
其实就是目前 qiankun 拦截了动态往 head 里插的 style 节点,但是 styled components 第一个以后的动态 style 节点不是往 head 里插的,是往前面插入的最后一个 style 节点后面插的,因此拦截不到。
其实就是目前 qiankun 拦截了动态往 head 里插的 style 节点,但是 styled components 第一个以后的动态 style 节点不是往 head 里插的,是往前面插入的最后一个 style 节点后面插的,因此拦截不到。
@xxn520 问题解决了吗,能请教下解决方案么?也遇到相同问题,styled-components再rebuild的时候某些样式丢失了。
@chenqiangmingyu 升 5 目前能解决多个 style 节点带来的问题,但是升 5 后,在应用切换的时候,StyleSheet 里面的 Tag 里面的 sheet 对象持有的还是老的引用,会导致新的样式插不进去(这应该也就是你提到的某些样式丢失的原因),目前的解法是在应用卸载的时候调用一下 StyleSheet.clearTag 方法清空 Tag,那么在应用切回来的时候 Tag 会重新创建,sheet 对象也会更新。但是进一步会有新的问题,我们无法比较好的控制 clearTag 的时机,如果用了 styled components 的 global styles,这个东西卸载的时机如果在 clearTag 之后又会报新的错。总得来说这两个东西有点水土不服,可能会 fork 其中一个来改了。
能提供一个可复现的仓库吗 @chenqiangmingyu @xxn520
@kuitos https://github.com/xxn520/qiankun/tree/master/examples 实际情况比这个复杂,但 dynamicHeadAppend 的问题这个例子也能够复现
能提供一个可复现的仓库吗 @chenqiangmingyu @xxn520
@kuitos @xxn520 我这边问题点已经fixed了,主要是子应用的容器是父应用动态生成的,父应用技术栈是React,因为父应用渲染由自身router控制,不受qiankun生命周期约束,导致location切换时把子应用的宿主容器给直接销毁,子应用unmount钩子执行与DOM容器清理并没有按照预期的顺序执行。容器清理后,待缓存的style节点也一并被粗暴的从DOM清理了,此后unmount读到的style可能由于gc之类机制出现了残缺(style.sheet === null),重建的样式也就异常了。
解决方案:这边把子应用容器作为一个常驻容器扔到父应用组件,不再销毁。 重建时产生另外一个问题就是cssRules和bootstrap的顺序正好相反造成的样式异常已经另开issue.
@kuitos https://github.com/xxn520/qiankun/tree/master/examples 实际情况比这个复杂,但 dynamicHeadAppend 的问题这个例子也能够复现
+1,楼主这个是可复现仓库,请 @kuitos 能尽快解决,感谢
@chenqiangmingyu 升 5 目前能解决多个 style 节点带来的问题,但是升 5 后,在应用切换的时候,StyleSheet 里面的 Tag 里面的 sheet 对象持有的还是老的引用,会导致新的样式插不进去(这应该也就是你提到的某些样式丢失的原因),目前的解法是在应用卸载的时候调用一下 StyleSheet.clearTag 方法清空 Tag,那么在应用切回来的时候 Tag 会重新创建,sheet 对象也会更新。但是进一步会有新的问题,我们无法比较好的控制 clearTag 的时机,如果用了 styled components 的 global styles,这个东西卸载的时机如果在 clearTag 之后又会报新的错。总得来说这两个东西有点水土不服,可能会 fork 其中一个来改了。
@xxn520 请问StyleSheet.clearTag
指的是子应用 unmount 的时候,把所有 <style>
remove 吗?
通过将 SC_DISABLE_SPEEDY=true
,可以使 <style>
里的内容在生产环境下也展示出来。可以避开 qiankun 在rebuildCSSRules 时对 styled components 的特殊处理。重新加载子应用时 styled components 也可以正确找到文件插入样式。可以解决我样式丢失的问题
@chenqiangmingyu 升 5 目前能解决多个 style 节点带来的问题,但是升 5 后,在应用切换的时候,StyleSheet 里面的 Tag 里面的 sheet 对象持有的还是老的引用,会导致新的样式插不进去(这应该也就是你提到的某些样式丢失的原因),目前的解法是在应用卸载的时候调用一下 StyleSheet.clearTag 方法清空 Tag,那么在应用切回来的时候 Tag 会重新创建,sheet 对象也会更新。但是进一步会有新的问题,我们无法比较好的控制 clearTag 的时机,如果用了 styled components 的 global styles,这个东西卸载的时机如果在 clearTag 之后又会报新的错。总得来说这两个东西有点水土不服,可能会 fork 其中一个来改了。
@xxn520 请问
StyleSheet.clearTag
指的是子应用 unmount 的时候,把所有<style>
remove 吗?通过将
SC_DISABLE_SPEEDY=true
,可以使<style>
里的内容在生产环境下也展示出来。可以避开 qiankun 在rebuildCSSRules 时对 styled components 的特殊处理。重新加载子应用时 styled components 也可以正确找到文件插入样式。可以解决我样式丢失的问题
我也遇到了同样的问题。但项目里面用的是 css module ,SC_DISABLE_SPEEDY=true 是在哪里设置呢,是放在 umi 项目的根目录 .env 文件吗?我还尝试过加 REACT_APP_SC_DISABLE_SPEEDY=true 都不生效
在umi-plugin-qiankun中,设置 sandbox:false 发现可以解决这个问题
@chenqiangmingyu 升 5 目前能解决多个 style 节点带来的问题,但是升 5 后,在应用切换的时候,StyleSheet 里面的 Tag 里面的 sheet 对象持有的还是老的引用,会导致新的样式插不进去(这应该也就是你提到的某些样式丢失的原因),目前的解法是在应用卸载的时候调用一下 StyleSheet.clearTag 方法清空 Tag,那么在应用切回来的时候 Tag 会重新创建,sheet 对象也会更新。但是进一步会有新的问题,我们无法比较好的控制 clearTag 的时机,如果用了 styled components 的 global styles,这个东西卸载的时机如果在 clearTag 之后又会报新的错。总得来说这两个东西有点水土不服,可能会 fork 其中一个来改了。
@xxn520 请问
StyleSheet.clearTag
指的是子应用 unmount 的时候,把所有<style>
remove 吗? https://stackoverflow.com/questions/53486470/react-styled-components-stripped-out-from-production-build 通过将SC_DISABLE_SPEEDY=true
,可以使<style>
里的内容在生产环境下也展示出来。可以避开 qiankun 在rebuildCSSRules 时对 styled components 的特殊处理。重新加载子应用时 styled components 也可以正确找到文件插入样式。可以解决我样式丢失的问题我也遇到了同样的问题。但项目里面用的是 css module ,SC_DISABLE_SPEEDY=true 是在哪里设置呢,是放在 umi 项目的根目录 .env 文件吗?我还尝试过加 REACT_APP_SC_DISABLE_SPEEDY=true 都不生效
最后发现是 qiankun v2.7.2 更新导致,回退到v2.7.0正常
What happens?
qiankun 和 styled components 一起使用时,当 styled components 插入动态样式时,样式量多时会为一个应用插入多个 style 节点,第一个 style 节点以后的 style 节点不是往 head 中插入的,因此 qiankun 的 dynamicHeadAppend 拦截不到。这导致在应用切换的时候,未拦截到的动态的 style 节点将会丢失,导致 styled components 报错。
相关环境信息