總結程序員(yuán)的幾大經驗教訓

發布時(shí)間(jiān):2023-11-07 | 編輯:深圳網站(zhàn)建設公司

第一(yī)、保障安全刻不容緩


保障安全刻不容緩,你不能(néng)輕描淡寫地說(shuō):“今後系統會加強安全性。”


強大的應用程序安全應該被當作(zuò)開發過程中的首要問題,應該從第1天開始就(jiù)需要討(tǎo)論,絕對不能(néng)等到第300天。将安全性留到最後一(yī)分(fēn)鍾實際上(shàng)會增加開發的時(shí)間(jiān),因為(wèi)你不得不返工,通過重構實現(xiàn)安全要求。


更糟糕的是,屆時(shí)你就(jiù)沒有那麽多時(shí)間(jiān)來(lái)解決安全問題了(le),最終隻能(néng)發布易受攻擊的代碼。雅虎等公司的遭遇就(jiù)是前車之鑒。


每個(gè)應用程序各不相同,且有各自的需求,根據應用程序的需求選擇,不要屈服于市(shì)場(chǎng)流行度。


每個(gè)應用程序各不相同,這(zhè)點無需多說(shuō)。世上(shàng)沒有一(yī)套适用于所有應用程序的萬全之策。在啓動新(xīn)應用程序時(shí),應該由應用程序及其體(tǐ)系結構來(lái)規定使用的技術或标準化(huà)的平台。


如(rú)果在你搞清楚“應用程序需要什(shén)麽”之前,就(jiù)決定使用gRPC或Kubernetes系統,那麽隻會阻礙代碼的編寫工作(zuò)。這(zhè)就(jiù)是為(wèi)什(shén)麽Canonical等公司誤入歧途,在物聯網設備上(shàng)運行Kubernetes。


引用Jeff Goldblum的一(yī)句話(huà):“科學家們忙于思考他們能(néng)夠幹什(shén)麽,不能(néng)夠幹什(shén)麽,以至于他們沒有時(shí)間(jiān)停下(xià)來(lái)思考是否應該這(zhè)樣幹。”


第二、你可能(néng)并不需要微服務(wù)


微服務(wù)非常有魅力,我完全理(lǐ)解。即便隻是想一(yī)想能(néng)夠單獨擴展應用程序中的各個(gè)小功能(néng),就(jiù)足以讓人(rén)興奮不已,因為(wèi)你可以感受到滿滿的成就(jiù)感。


但(dàn)是,說(shuō)實話(huà)你可能(néng)不需要微服務(wù)。比如(rú)“我希望将功能(néng)X的代碼從功能(néng)Y的代碼中分(fēn)離出來(lái)”,“防止不良代碼滲透到應用程序的其他部分(fēn)”,或者“最小化(huà)受影響的應用”等到這(zhè)些(xiē)理(lǐ)由不是使用微服務(wù)的原因,這(zhè)些(xiē)不過是糟糕的開發實踐導緻的惡果,你需要的是更嚴格的代碼審查标準(不要合并不良代碼),以及更為(wèi)細緻的安全控制。


你是否需要單獨擴展應用程序的各個(gè)部分(fēn),而且目前的組件(例如(rú)登錄流程)是否存在容量的問題?然後再探索那些(xiē)需要擴展成獨立服務(wù)的組件。


你是否需要運行基于虛拟服務(wù)器(qì)的架構并希望降低(dī)成本?如(rú)果是,那麽就(jiù)不應該探索微服務(wù)。即便采用微服務(wù),充其量也(yě)不過是功過相抵。惡劣的情況下(xià),最終隻是多了(le)幾個(gè)需要單獨啓動的實例。


假設你的整體(tǐ)式架構包含5個(gè)服務(wù),而你卻将其分(fēn)解成了(le)微服務(wù)。那麽,現(xiàn)在你有5個(gè)應用,你所面臨的局面是:


a)你需要逐個(gè)啓動專用實例,而占空的空間(jiān)是最初的5倍;


b)你利用現(xiàn)有的空間(jiān),同時(shí)承擔額外的運營成本。


第三、标準化(huà)的開發環境


在與多個(gè)開發人(rén)員(yuán)合作(zuò)時(shí),标準化(huà)整個(gè)團隊使用的開發環境可以讓你受益無窮。我并不是說(shuō)你必須将一(yī)些(xiē)基于容器(qì)的虛拟開發環境通過魔法混合在一(yī)起。雖然你要這(zhè)麽幹我也(yě)攔不住,但(dàn)是你隻需使用同一(yī)個(gè)版本的語言就(jiù)可以為(wèi)團隊帶來(lái)奇迹。


如(rú)果你的同事(shì)用Go 1.11編寫代碼,而你卻在Go 1.12上(shàng)發現(xiàn)了(le)Bug,那麽可真是欲哭無淚。協調何時(shí)升級版本可能(néng)很困難,但(dàn)一(yī)旦協調成功,諸事(shì)都會順利。


第四、配置的工作(zuò)不簡單,請務(wù)必做好(hǎo)(hǎo)相應的計劃


雖然有些(xiē)流行的網站(zhàn)說(shuō),配置隻不過是“将所有東西(xī)都扔進環境變量中”,然而事(shì)實遠(yuǎn)非如(rú)此。


我認為(wèi)配置應用程序的方法至少有四種:代碼内的默認值、本地配置文件、命令行的标志、環境變量、遠(yuǎn)程配置(如(rú)使用Hashicorp的Consul)等。我認為(wèi)遠(yuǎn)程配置是可選的,而其他四個(gè)都是必要的。


對于開發來(lái)說(shuō),為(wèi)了(le)在本地運行應用程序而不得不将27個(gè)不同的配置值放(fàng)入環境變量,這(zhè)會讓人(rén)萬分(fēn)沮喪。另外,你可能(néng)需要更好(hǎo)(hǎo)的自動化(huà)和Makefile。你可以利用本地配置源的方法,如(rú)application.yaml,并默認設置為(wèi)“dev”配置。


此外,如(rú)果深圳網站(zhàn)建設公司代碼中有默認值,則意味着你需要更改它們的默認值。在通過systemd等初始化(huà)系統運行應用程序時(shí),命令行的标志非常實用,因為(wèi)在查看進程的運行情況時(shí),你可以清楚地看到應用程序的配置方式。在容器(qì)内運行應用程序時(shí),環境變量非常實用,但(dàn)也(yě)有一(yī)些(xiē)東西(xī)不适合放(fàng)入環境變量,比如(rú)Secret。


你永遠(yuǎn)不能(néng)将Secret(密碼、身(shēn)份驗證令牌、證書等你不想洩露給公衆的數據)放(fàng)入環境變量,因為(wèi)它們不安全,而且主機上(shàng)的任何進程都可以讀取環境變量。你應該借助某種Secret管理(lǐ)工具。我個(gè)人(rén)喜歡使用Vault(來(lái)自Hashicorp),但(dàn)你可以根據應用選擇最合适的工具。


第五、隻在必要時(shí)導入軟件包


我們都知道left-pad的那個(gè)故事(shì)吧(ba)(https://www.theregister.co.uk/2016/03/23/npm_left_pad_chaos/)。


隻因為(wèi)有人(rén)從代碼倉庫中删掉了(le)一(yī)個(gè)11行的NPM軟件包,結果幾乎導緻整個(gè)互聯網癱瘓。


請務(wù)必小心。隻有當你面臨正當的需求時(shí),才應該導入軟件包,例如(rú)某個(gè)供應商(shāng)特定的SDK(比如(rú)AWS的SDK),這(zhè)是一(yī)組高度冗長的标準庫抽象(這(zhè)就(jiù)是人(rén)們喜歡使用Python的請求而不是urllib的原因) ,或廣泛使用的框架,比如(rú)Go的Echo HTTP服務(wù)器(qì)或Python的Flask WSGI服務(wù)器(qì)。


一(yī)些(xiē)便捷的庫也(yě)可以,比如(rú)JavaScript的Lodash提供了(le)标準庫中沒有的一(yī)些(xiē)常用功能(néng)和附加功能(néng)。這(zhè)些(xiē)外部的依賴項可以減輕開發的負擔,而且你不需要手動編寫樣闆或集成代碼,這(zhè)些(xiē)都是包系統的優勢。然而,就(jiù)像left-pad一(yī)樣,你很容易被坑:“這(zhè)兒(ér)有一(yī)個(gè)庫,我可以使用。”你導入的依賴項每增加一(yī)個(gè),随之而來(lái)的不穩定性和風(fēng)險也(yě)會劇(jù)增,可能(néng)這(zhè)些(xiē)庫根本沒人(rén)維護。

22

新(xīn)依賴項本身(shēn)導入的每個(gè)包也(yě)會增加風(fēng)險,這(zhè)稱之為(wèi)傳遞依賴。如(rú)果你導入了(le)一(yī)個(gè)包,而這(zhè)個(gè)包又導入了(le)5個(gè)包,那麽恭喜你現(xiàn)在繼承了(le)這(zhè)五個(gè)依賴關(guān)系以及随之而來(lái)的所有風(fēng)險。


我和這(zhè)個(gè)行業的許多其他人(rén)都認為(wèi)軟件包不應該引入傳遞依賴。雖然無法做到萬無一(yī)失,但(dàn)至少應該盡可能(néng)減少,如(rú)果你需要更多功能(néng),那麽就(jiù)為(wèi)用戶提供一(yī)種明确的擴展方法。


在導入庫時(shí),通常我會遵循一(yī)個(gè)簡單的規則:如(rú)果我可以在10-15分(fēn)鍾内自己編寫,那麽就(jiù)自己寫;否則再考慮使用外部的庫。


在開發的時(shí)候,牢記這(zhè)條規則可以避免将不必要的内容導入應用程序,但(dàn)是你不必每次需要提供API時(shí)都考慮從頭開始編寫新(xīn)的HTTP服務(wù)器(qì)。


第六、沒必要抽象所有代碼


還有一(yī)個(gè)很大的坑:抽象一(yī)切。


有時(shí),你會覺得“稍後我可能(néng)會再用到這(zhè)個(gè)功能(néng)”,這(zhè)個(gè)想法可能(néng)會将你引向一(yī)條黑暗又可怕的面向對象之路(lù)。


DRY原則(Don’t Repeat Yourself,不要自我重複)徹底征服了(le)我們,盡管這(zhè)條原則有其充分(fēn)的理(lǐ)由。


然而,你需要注意不要在抽象上(shàng)花費太多時(shí)間(jiān),以至于沒有足夠的時(shí)間(jiān)編寫邏輯。你的工作(zuò)是寫代碼!等到你發現(xiàn)你需要實現(xiàn)的某個(gè)方法或函數之前已經寫過了(le),那麽可以再回過頭來(lái)抽象,但(dàn)是切記量力而行。


我個(gè)人(rén)遵循的原則是,如(rú)果抽象之前隻是一(yī)個(gè)隻有3行的函數,那麽就(jiù)重複好(hǎo)(hǎo)了(le)。如(rú)果真的隻有3行代碼,也(yě)許你該想一(yī)想是否值得寫成函數。


第七、項目需要像“鳳凰”一(yī)樣,


經曆浴火(huǒ)重生(shēng)的洗禮


這(zhè)個(gè)想法令人(rén)不寒而栗。經理(lǐ)們會為(wèi)此感到緊張,産品所有者會為(wèi)此變得暴躁,而且開發人(rén)員(yuán)也(yě)會因此而感到憤怒,但(dàn)你必須這(zhè)麽做。


每隔一(yī)段時(shí)間(jiān)就(jiù)從頭開始其實是一(yī)件好(hǎo)(hǎo)事(shì)。你可以借機删掉代碼中的冗餘,而且無需改造現(xiàn)有的半個(gè)代碼庫就(jiù)可以實現(xiàn)新(xīn)的想法,同時(shí)還可以強制每個(gè)人(rén)重新(xīn)評估項目。


你可以把項目想象成一(yī)片森林,每一(yī)行代碼都是一(yī)棵參天大松樹,綿延數裏。随着時(shí)間(jiān)一(yī)天天過去,這(zhè)片森林會布滿灌木叢、飄落的松針、松果、枯枝和許多其他雜物。這(zhè)些(xiē)都是你的麻煩,你的技術債務(wù)。


這(zhè)些(xiē)東西(xī)越積累越多,直到受到某種外部力量的影響。對于森林而言,這(zhè)種外部力量就(jiù)是野火(huǒ)。火(huǒ)焰肆虐過的森林,地表寸草不生(shēng),隻有樹皮足夠厚的樹木才能(néng)存活下(xià)來(lái),所有未長成的樹木都會被大火(huǒ)燒盡。雖然這(zhè)對森林來(lái)說(shuō)是滅頂之災,但(dàn)其中蘊含着一(yī)個(gè)驚天的秘密:森林渴望大火(huǒ)。多年來(lái),它一(yī)直在耐心地等待,等待火(huǒ)焰來(lái)淨化(huà)一(yī)切,因為(wèi)火(huǒ)焰在樹冠下(xià)肆虐過後,下(xià)一(yī)代的參天大樹才會從松果中發芽。


當火(huǒ)焰橫掃過森林地面時(shí),它會孵化(huà)出幼小脆弱的樹苗,讓它們與被大火(huǒ)燒得漆黑的幸存者并肩而立。你的應用程序也(yě)需要這(zhè)樣的洗禮:生(shēng)命力旺盛、編寫良好(hǎo)(hǎo)的代碼會從清理(lǐ)中存活下(xià)來(lái),而新(xīn)的想法和代碼會從累累白骨中站(zhàn)起來(lái),宛如(rú)浴火(huǒ)重生(shēng)的鳳凰。



版權保護: 本文由深圳網站(zhàn)設計公司發布,轉載請保留鏈接: 總結程序員(yuán)的幾大經驗教訓
如(rú)有内容侵權,請聯系我們。