当前位置: 首页 > 科技观察

一个关于建筑的“说说”

时间:2023-03-18 01:21:30 科技观察

作者|段和臣的文章标题很随意,有点“贼”的意思骗点击;但内容充满诚意,想必你也感受到了。这是一篇讨论Android客户端软件架构的头条新闻。之所以取名“口枪”,是因为它有退路;同时混合了一些方法论,不仅适用于客户端软件架构,也适用于其他工作场景,希望对大家有所帮助。为了填补读者的沉浸感,我们以“我们”为主体,来看看结构上的挑战、判断和策略。我们的挑战期望高而优秀的公司对架构有很高的期望。他们都希望有好的顶层设计,上下有统一的认知,遵循共同的规范,写出舒服的代码,甚至有没有懒惰这样的东西,有没有“一劳永逸”的架构设计那能保证地基长寿?然而,高期望意味着高差距,面对差距,我们很容易焦虑:什么时候才能把代码写成它应该有的样子?;但为什么现在就像爬“狗屎山”一样?文档什么时候可以写得简明扼要;可现在为什么简明扼要难懂,细节又是多余的呢?该工具什么时候会更实用、更详细?更强;但是现在为什么不能动不动就掉链子,一年到头等着自己想要的功能排期呢?“我”什么时候才能在建筑工作中找到成就感,而不是干完就想着逃跑?责任重大大量问题的最终归因是代码问题:设计不合理、使用不规范、逻辑过于晦涩、编码“pitch”过多。这些问题没有任何一个团队可以承担责任,我们收到了很多“吐槽”:谁写的,简直不堪入目,让我展示一下我的真实实力XX埋在这里是个雷,但XX不在乎它了。现在,我只能做点什么了。根本不应该以这种方式使用它。最初的设计不是为了这个场景。是在逗我吗?卧槽,这到底是什么隐藏技能。我在编译的时候悄悄改了老子的代码,却找不到穿透的地方,也意味着责任也转嫁到我们身上:如果我们处理得好,我们的产出可能仍被视为糟粕,但如果处理不好,我们将毁掉企业发展的前途。困难的事情架构从来都不是面对单一业务的问题,而是多业务多人协作的横切问题,负重前行是常态。生意经久不衰,历史包袱叠加新场景,一刀拔萝卜带泥。例如:2021年10月版今日头条有XXXX个分量,比一年前翻了一番;班级数为XXXXX;插件数量为XX;仓库数量为XX;ttmain仓库权限为XXX人。(XX代表数量级,具体数字隐藏了,^_^)技术栈层出不穷。一方面要保持成熟稳健,另一方面要积极探索和落实。架构同学应该熟悉多种技术栈,例如:跨端技术通常在客户端业务中并存(H5/Hybrid/applet/Lynx/Flutter),一个业务应该使用哪种技术栈,需要多少成本?技术栈选定后有哪些局限性,有没有什么不可逾越的障碍?疗效缓慢。我们常说代码复杂度高,把降低复杂度作为架构方向的重点任务之一;有很多因素。从外部来看,主要有主观体验、客观指标、行业对标三个方面;从内部来看,有工程组织、代码实现、技术栈三个角度。即使我们把工程结构的因素优化得很好,也很难在短时间内感受到复杂度的明显下降。我们经常讲治理,其实是设计一个机制,在这个机制下运行,直到治好。就像老中医开的药方,开的不是特效药,而是对症下药。药方是否有用,还需要经过实践和时间的检验。希望我们不要成为江湖郎中,抓几把药炖着吃,吹嘘药能治病。我们常说架构问题谁来review,难免要炒“冷饭”;谁规划架构方向,谁就逃不开“减负”、“重构”、“复用”、“标准化”。”这些关键词。难点在于把冷饭再加热,落实方向。架构方向一直存在,架构不局限于一个产品的初始阶段,而是伴随着产品的整个生命周期。”架构不是一成不变的,它只适用于特定的场景,过去的架构不一定适合现在,现在的架构未必能预知未来,架构是随着业务不断演进的,不会有架构方向,当事情可以做的时候,结构总是充满活力的。强制规范合规:通常要求通用业务组件逐渐下沉到基础组件层,但随着时间的推移,这个规范很容易被打破。需要成熟的团队:领域专家(非常熟悉业务细节的角色)和开发团队需要紧密合作,构建核心domain模型是关键。但盲目尝试DDD往往容易低估领域驱动设计方法论的实际成本,例如将简单的问题复杂化,陷入过分强调技术模型的陷阱迄今为止,商业应用最流行的软件架构设计模式是DamuBigBallofMud(BBoM),BBoM是“……一个随意构建、随意、凌乱、随意拼贴、毫无头绪的代码丛林。”泥球模式会扼杀开发,即使重构让人担心,但也被认为是理所当然的。但是,如果仍然缺乏对领域知识应有的重视和考虑,新的项目最终会走向泥球。没有开发者愿意和一个大泥球打交道,而对于一个企业来说,陷入大泥球就意味着失去了快速实现商业价值的能力。——《领域驱动设计模式、原理与实践》ScottMillett&NickTune复杂系统的熵不断增加。只要业务不断发展,越来越复杂是必然趋势,符合热力学熵增规律。复杂性熵增加的过程可以从两个维度看:理解成本变高,预测难度变大。理解成本:规模和结构是影响理解成本的两个因素。规模之大,难以理解。例如,在城市道路网络中很容易迷路,而在农村就很难理解仅仅几条道路的复杂结构,例如:时钟比一条内衣更难理解。当需求增加时,软件系统的规模也会增加,而且这种增长趋势不是线性的,而是会更陡峭。如果需求出现不可预见的变化,而我们又没有足够的风险应对措施,在时间紧迫的情况下,难免会在设计上妥协,头疼腿脚,在系统的各个地方打补丁,从而欠下技术债务(TechnicalDebt)。当欠下的技术债越来越多,积累到某个临界点时,量变会引起质变,整个软件系统的复杂度就会达到顶峰,进入老年期衰落并成为一个“可怕的”遗留系统。就像饲养场里的“奶牛法则”:奶牛逐渐衰老,最终无奶可挤;然而,与此同时,饲养成本也在上升。——《实现领域驱动设计 - 深入理解软件的复杂度》张艺难度预测:目前的筹码不足以应对未来的变化。业务变化是不可预测的。例如:今日头条一开始只是一个单端的咨询流产品。5年前没有人会预先设计精简版,、点车滴等,多终端和新业务场景带来的变化难以预料。很多时候,我们此刻只需要做到“合适”的架构设计,而是尽可能地维护“秩序”。一旦我们脱离了“秩序”,必然会导致混乱,变得更加难以预料。技术变化是不可预测的,例如:作为Java开发者,Lambda表达式的简洁,函数式编程的乐趣,声明式/响应式UI的体验,都是“真香”的技术变化,老Java版本和配套依赖requireUpgrade,一旦升级,伴随着多版本共存、依赖地狱(转移升级)等可怕的问题。很多时候,我们不需要也不可能进行未来的技术架构设计,但我们需要让架构保持“清晰”,这样才能更快地拥抱技术变革。既然注定是逆风,那我们终究会赢。过多的工艺规范会让大家觉得自己是木偶,而木偶注定会随风而逝。我们应该更多地“强调”一些原则,比如:分而治之,控制规模,保持结构的清晰和一致,而不是要求每个人都按照某种准则进行建筑设计,这样既不能降低复杂性,也不能保持多样性.“强调”不是直接解决问题,而是突出重要的问题,让大家在一定的原则下,自己找到解决问题的方法。我们的打法我们的套路是:定义问题→确定结构→实施方案→评审结果。前面的步骤越多,越重要和抽象,难度越大,越能体现架构师的功力。所以,我们打球的第一步就是认清问题。认识到问题分类结构的问题是相互交织的,当所有问题放在一起时,就会有优先级和类别。通过区分问题的类别,可以在一定边界内匹配对应的人来解决问题。工程架构:业务架构:基本能力:标准化:问题分类挑战、问题、手段常常混淆。哪些是挑战?哪些是问题?那些是手段?其实这些都是一样的东西,就是矛盾,只是在不同的场景下,矛盾的程度是不一样的。我举个例子:我们判断目前的研发经验不能满足业务拓展的需要。这是一个矛盾,既是当前的挑战,也是当前的首要问题。为了处理这个矛盾,我们不得不对其进行反汇编,于是就有了一个二级问题:我们的代码逻辑是否足够优化?研发过程是否足够方便?文档工具是否足够完整?二级问题也是矛盾,需要解决好的二级问题,就是我们处理一级矛盾的手段。这样一层层往前,我们可以掌握一些目前需要重点优化建设的基础能力:插件、热更新、跨终端能力。在具体实践过程中,基础技术能力还是需要拆解的。比如热更新能力有很多(Java层的Robust/Qzone超级补丁/Tinker,Native层的Sophix/ByteFix等),不同的热更新方案各有优缺点,适用场景也不尽相同相同。我们要根据现状做出判断,借鉴众多方案的长处,或者进行更大的技术突破和创新,或者整合现有的技术方案进行联合创新。勤奋思考问题背后的问题亨利福特说,如果我问我的客户他们想要什么,他们告诉我他们需要一匹更快的马。从亨利·福特的话中,我们可以提炼出一个最直接的问题:客户需要一匹更快的马。基于这个问题本身寻找解决方案可能永远不会得出令人满意的答案:寻找更好的品种和更科学的训练马匹的方法。思考问题背后的问题,为什么客户需要一匹更快的马?也许客户想要一种更快的日常交通方式。升到一个级别后,我们马上找到了更好的解决方案:造车。我们不能只局限于问题本身,还需要看到问题背后的问题,才会更容易找到更多的解决方案。认知金字塔用认知金字塔的模型来鼓励我们从最原始的数据中提炼出解决问题的智慧。数据:金字塔的底部是数据。数据代表各种事件和现象。数据本身没有组织、结构或意义。数据只能告诉你发生了什么,而不能告诉你为什么会发生。INFORMATION:数据的上层是信息。信息是结构化数据。信息对分析和解释很有用。知识:信息的下一个层次是知识。知识组织信息并告诉我们事件之间的逻辑联系。知道云会导致下雨,因为下雨天气会变凉。成语、典故、思维套路都是知识。模型可以说是一种高深的知识,可以解释一些事情,做出预测。智慧:认知金字塔的顶端是智慧。智慧是认识和选择相关知识的能力。你可能掌握了很多模型,但是具体到这个问题用哪个模型,你敢不敢用这个模型就是见仁见智了。这就是“DIKW模型”。分步架构的问题不能等,也不能急。一个大型的应用软件并不需要所有的部分都设计得非常完美。对于一些低复杂度地区或不太可能耗费能源的地区,满足现有条件即可,不需要投入高质量的建设成本。以治理头条复杂度为例:长期架构目标:更宽(多端复用)、更快(单端开发速度)、更好(问题清洗和预阻)当前突出问题:业务间耦合度过高Heavy,缺乏标准规范,代码冗余和晦涩的细节已经编码,请不要关心它。关键是问题弄清楚后,会螺旋上升,这样长期有方向,短期有反馈。最后一顿饭产出后,一定不能忘记人文关怀,毕竟说了算的还是人。建筑雄狮不得不承认,他们高瞻远瞩,运筹帷幄;但是建筑师更需要被照亮,他们可能常年在“铲屎”,他们期望被认可,他们中的一些人没有合作伙伴......做吧,建筑的故事仍然存在,但人似乎已经翻过这一页。