最近因为Vibe Coding产品,在速成前端核心概念,发生真的很有美感;
感慨人类的智慧,且这样的智慧今天版本的LLM是根本上无法做到,因为这是一种新抽象的美感,做约束做减法做抽象,而非一昧的去做加法补丁
顺带的,也明白了Notion的伟大之处,绝不单纯是一个「Block」的产品层面的概念创新,而是产品-前端-后端 跨层级的创新
A - 前端本质到底在解一个怎样的问题?
先说我理解到答案:是极致速度性能需求下,快速进行排版,并且渲染需要的界面(html/css - DOM,都是为了解决这个问题
我一开始是困惑的,大家都说当年浏览器吃掉了大部分桌面操作系统的市场,Windows当年为了狙击网景,紧急推出IE
可是操作系统也有自己的图形界面呀?另外今天回头看甚至有Electron这样的网页套壳桌面端的框架,网页/浏览器 的魅力到底在哪里?
一个很简单的回答是兼容性,但是仅仅是兼容性吗?可能有点太浅了
我问AI的第一个问题:为什么DOM是树状结构呢?以及html/CSS这种语言到底设计背后的意图是什么
AI和我说,如果我们引入一个图灵语言来表达前端的话,那么很容易就遇到停机问题,也就是说你不确定到底这个排版问题,到底能不能结束,那浏览器很有可能就卡死在渲染上
如果强制要求传入的是树状DOM的话,那么就可以肯定这里是没有循环,是不会停机的;
图像计算本身就要比后端多了N倍的计算量,回想早年的计算机,也只有强制做这样的内容形式约束,才能在根源上节省时间
于是我明白了:
1)前端本质是要解决高效率的画面渲染问题,为了达成这个问题,我们贯彻整个技术链路都需要做一些约束
2)DOM是树状结构,只有这样,才可以绝对不死机的去快速渲染成画面
3)因此,html语言本身也就是一个表述树状节点的语言结构
我又问AI第二个问题:那CSS到底在做什么,为什么要和Html分开?
AI先给我讲解了下浏览器的一个核心功能,是排版功能;HTML约定了整体的DOM后,即有哪些节点之后;CSS来约定这2件事:每个节点的Box(容器)应当有怎样的尺寸约束,这个约束可以是Box之间的排版关系,也可以是某个具体的尺寸;另外一个则是Box有怎样的视觉语言(材质/颜色等)
浏览器之所有可以做到不同设备兼容运算,实则是因为CSS的功劳;写网页的人并不想需要实际考虑用户的硬件尺寸到底有多大,而是只需要在CSS里给一些相对排版约束;浏览器再实际结合用户界面,去进行排版运算(这里也有一些核心排版算法 + 效率优化)
而HTML和CSS分离的原因也非常简单,你如果要换排版或者视觉规范,但是元素的树状关系如果没有变化,就无所谓
于是我明白了:
1)前端的本质,是为了在不同的硬件终端,实现同样规范的高效率「排版」
2)浏览器做的核心工作之一,是基于DOM+挂载的CSS里内涵的排版约束,进行高效率最终的画面排版运算
3)大家所谓的兼容性,一份代码多端运行,在前端层面,主要就靠浏览器;因此浏览器实则是一个画面渲染的「解释器」
我问AI的第三个问题,是关于JS的,js为什么要出现呢?
AI回答我:这个就比较简单了,你后端有数据变化,客户端可能用户交互也有数据变化,html显示的内容、css的样式都需要变化;每次都重新拜托服务器传一份新的html效率多低,不如直接本地计算
虽然说前面聊到画面渲染不要用图灵完备的语言;但是具体的文字/数字等,倒是可以用脚本来实现的,于是就有了js出现了
js还有一些专用的能力:IO交互(因此是异步原生的?);网络通信
而当年Google Chrome的厉害之处,就是写了个V8引擎,直接把js的效率拉高了N倍(同样是速度),最后还导致了Node.js的产生,以及再后续的Typescript(js设计实在是太草台班子了,语法有点烂,所以打了补丁成了TS)
到这里为止,我们大致就了解了
1)浏览器为了实现动态的画面布局设计,最后也在数据层引入了一门新的图灵完备的语言
2)速度速度速度,不变的依然是速度
B - 前端技术栈到底在做怎样的抽象?
这里我就不引入问题/回答的方式了,太长了,我直接写聊出来的结果
再后面,前端技术栈经历了2次的抽象变化;第一次是MVC的抽象(关注点分离),第二次则是React代表的组件化倾向(每个组件都是一个内聚的MVC)
人们写代码写到后面,发现网页越来越复杂,如果每个都手搓html和css还有js,会变得很复杂
然后于是人们就有了一些新的框架,大致都是在做这样一个事情:让我们把数据模型(后端传输过来的数据重新洗做编排),画面该如何展现,以及如何最终如何控制/交互等,分离成这3个切面
每个切面分开去约定,再去让编译器编译成html/css/js就好了
等于在这里开始,就出现了新的一层封装,原本的html/css/js如果说是在针对排版层(浏览器)进行封装的话
MVC则是针对一定规模复杂的前端网页做抽象,大致也许是因为数据/画面复杂到一定程度,我们需要分成3个方面分别约束
再到后面,Facebook的工程师写页面发现,一个画面也不能简单拆解为MVC这几个切面
比如说:有消息弹出来的小红点,这个小红点本身内在就是一个MVC(有数据 - 提醒;有显示,有控制 - 点开就没有),我的对话消息框也有自己的MVC
如果我所有组件都混在一起写,就很复杂
于是就有了组件逻辑;每个组件都有自己的MVC,组件和组件当然也有某种树状关系
于是就有了更上一层的抽象:依然是一个画面,依然是元素拆解;不同于html/css的是,我这里每个元素都有复杂的数据逻辑和变化逻辑,因此我需要用到MVC这层抽象,但是我每个组件又是内聚的
总结:
1)变化的/交互的数据引入到页面中后,就需要切分成3个切面:MVC
2)更复杂的页面,类似于html DOM的抽象,但是这里每个元素都有复杂的数据逻辑,因此有了组件的概念
Final:
我觉得理解了这套范式后,再去看具体的产品,对于做这个产品逻辑的拆解也非常有帮助
甚至对于AI Coding的任务管理也有很大的帮助
比如你可以先去逐个组件的优化,再去做组合和拼接
至于Notion,则是基于这样的思想,一个全方面的创新
我一开始理解Notion的Block,觉得是不是就是把编程里的抽象概念简化了(类似于React的组件),告诉了广大非技术用户
是不是技术并没有什么创新?
直到我想做一个类似的设计后,我去和AI聊了聊,发现完全不是这样。。。
但是我写累了,下次心情好再写Notion的理解