不到 20 人的 IT 崗能待?。咳棵悦S矒?!
兄弟們,今天咱們來嘮嘮那些在「野生 IT 園」里的生存法則。當(dāng)你打開招聘軟件,看到 "扁平化管理"" 全棧開發(fā) ""快速成長" 這些關(guān)鍵詞時(shí),恭喜你,即將踏入一個(gè)左手寫前端右手改數(shù)據(jù)庫,白天寫代碼晚上修服務(wù)器的神奇領(lǐng)域 —— 不到 20 人的 IT 小團(tuán)隊(duì)。
一、小公司 IT 崗的真實(shí)畫像:在「野生叢林」里搞開發(fā)
(一)一人多崗的「全棧噩夢」
記得我入職第一周,老大拍著我肩膀說:"小張啊,咱們這兒沒那么多細(xì)分崗位,你平時(shí)除了寫后端,前端有問題也搭把手,數(shù)據(jù)庫優(yōu)化也盯著點(diǎn),對(duì)了,運(yùn)維腳本你也會(huì)寫吧?" 從此開啟了我的「全棧修仙之路」:早上用 Vue 改前端樣式,中午用 Spring Boot 調(diào)接口 bug,下午趴在服務(wù)器前用 Shell 排查內(nèi)存泄漏,晚上還要用 Jenkins 部署新功能。最魔幻的是有次線上數(shù)據(jù)庫鎖表,我居然用 Python 寫了個(gè)臨時(shí)監(jiān)控腳本應(yīng)急。
(二)「祖?zhèn)鞔a」的恐怖襲擊
每個(gè)小公司都有一套神秘的「祖?zhèn)鞔a庫」,里面藏著各種上古神器:用 Struts2 寫的核心模塊,XML 配置比代碼還長的 Spring 項(xiàng)目,還有不知道哪年寫的 SQL 腳本里混著拼音變量名。我曾在一個(gè) Service 層看到這樣的注釋:"這里不能改,上次小王改完整個(gè)系統(tǒng)崩了",旁邊還有 2018 年的 TODO:"這里需要優(yōu)化,等招到架構(gòu)師再說"。最絕的是有個(gè)工具類,里面同時(shí)存在 Commons Lang3 和 Apache Utils 的重復(fù)方法,問老員工才知道是不同時(shí)期入職的人各自帶的「嫁妝」。
(三)需求變更的「極限挑戰(zhàn)」
在小公司,需求文檔永遠(yuǎn)是「動(dòng)態(tài)更新」的。上午產(chǎn)品經(jīng)理說:"咱們做個(gè)簡單的用戶注冊(cè)功能",下午老板路過說:"加上短信驗(yàn)證和微信登錄",第二天客戶說:"還是改成郵箱注冊(cè)吧,另外需要支持海外手機(jī)號(hào)"。最刺激的是有次上線前三天,運(yùn)營突然說:"首頁要加個(gè)動(dòng)態(tài)特效,就像抖音那種滑動(dòng)切換",于是全團(tuán)隊(duì)開啟了「極限加班模式」,我一邊寫前端動(dòng)畫,一邊擔(dān)心后端接口能不能扛住突發(fā)流量。
二、技術(shù)突圍:小團(tuán)隊(duì)如何打造「迷你高效架構(gòu)」
(一)輕量級(jí)技術(shù)棧選型:小而美的「瑞士軍刀」
在資源有限的情況下,技術(shù)棧選型要像選瑞士軍刀一樣,既要功能全面又要輕便好用。后端我們選擇了 Spring Boot + MyBatis Plus 的黃金組合,Spring Boot 的自動(dòng)配置讓我們省去了大量繁瑣的配置工作,MyBatis Plus 的代碼生成器更是神器,半小時(shí)就能生成基礎(chǔ)的 CRUD 代碼,讓我們有更多時(shí)間處理核心業(yè)務(wù)。前端用 Vue2(別問為什么不用 3,因?yàn)樽鎮(zhèn)黜?xiàng)目)搭配 Element UI,快速搭建界面,而且社區(qū)資源豐富,遇到問題分分鐘能找到解決方案。
數(shù)據(jù)庫方面,主庫用 MySQL,畢竟小公司數(shù)據(jù)量還沒到需要分庫分表的地步,而且運(yùn)維成本低。緩存用 Redis,解決熱點(diǎn)數(shù)據(jù)訪問問題,比如商品詳情頁這種高頻訪問的接口,加上 Redis 緩存后,數(shù)據(jù)庫壓力驟減。消息隊(duì)列用 RabbitMQ,輕量級(jí),容易部署,像訂單異步處理、短信郵件發(fā)送這些場景都能輕松應(yīng)對(duì)。
(二)架構(gòu)演進(jìn):從「單體巨石」到「迷你微服務(wù)」
剛?cè)肼殨r(shí),整個(gè)系統(tǒng)是一個(gè)龐大的單體應(yīng)用,啟動(dòng)一次要三分鐘,打包后的 jar 包有 500 多 M,每次發(fā)布都提心吊膽,生怕哪個(gè)模塊出問題導(dǎo)致整個(gè)系統(tǒng)崩潰。隨著業(yè)務(wù)增長,我們開始了痛苦的架構(gòu)演進(jìn)之路。
首先進(jìn)行模塊拆分,把用戶中心、訂單中心、商品中心等獨(dú)立出來,變成一個(gè)個(gè)微服務(wù)。用 Spring Cloud Netflix 套件來實(shí)現(xiàn)服務(wù)治理,Eureka 做服務(wù)注冊(cè)與發(fā)現(xiàn),Ribbon 做負(fù)載均衡,F(xiàn)eign 做服務(wù)調(diào)用,Hystrix 做熔斷降級(jí)。考慮到小團(tuán)隊(duì)運(yùn)維能力有限,我們沒有上復(fù)雜的 K8s,而是用 Docker Compose 來管理容器,每個(gè)微服務(wù)打包成 Docker 鏡像,部署起來方便快捷。
在拆分過程中,遇到了很多坑,比如接口兼容性問題,舊接口還在被前端調(diào)用,新接口已經(jīng)改了參數(shù),只能做版本控制,在 URL 里加上版本號(hào),比如 /v1/user/getInfo。還有分布式事務(wù)問題,我們用了 TCC 模式和可靠消息最終一致性方案,雖然不如大公司的 Seata 那么完善,但在小團(tuán)隊(duì)里也能基本滿足需求。
(三)自動(dòng)化部署:讓「手動(dòng)發(fā)布」成為歷史
以前發(fā)布項(xiàng)目全靠手動(dòng)拷貝 jar 包到服務(wù)器,然后重啟服務(wù),不僅效率低,還容易出錯(cuò),有次把測試環(huán)境的包發(fā)到生產(chǎn)環(huán)境,導(dǎo)致用戶數(shù)據(jù)錯(cuò)亂,被老板狠狠批了一頓。痛定思痛,我們搭建了自動(dòng)化部署平臺(tái),用 Jenkins + GitLab + Docker 實(shí)現(xiàn)了 CI/CD 流水線。
開發(fā)人員提交代碼到 GitLab,Jenkins 自動(dòng)拉取代碼,編譯打包成 Docker 鏡像,然后推送到 Harbor 鏡像倉庫,最后通過 SSH 遠(yuǎn)程連接服務(wù)器,更新 Docker 容器。同時(shí),我們還集成了 SonarQube 進(jìn)行代碼質(zhì)量檢測,在構(gòu)建階段就檢查出代碼中的 bug 和代碼異味,避免問題代碼進(jìn)入生產(chǎn)環(huán)境。現(xiàn)在發(fā)布一個(gè)版本只需要點(diǎn)擊一下按鈕,十分鐘內(nèi)就能完成,而且有了回滾機(jī)制,萬一出問題也能快速恢復(fù)。
三、團(tuán)隊(duì)協(xié)作:小團(tuán)隊(duì)如何實(shí)現(xiàn)「高效配合」
(一)「麻雀雖小,五臟俱全」的流程建設(shè)
很多人覺得小公司不需要流程,大家口頭溝通一下就行,其實(shí)不然。沒有規(guī)范的流程,只會(huì)讓團(tuán)隊(duì)越來越混亂。我們制定了簡單實(shí)用的開發(fā)流程:需求評(píng)審→任務(wù)拆分→開發(fā)→自測→代碼審查→聯(lián)調(diào)→測試→預(yù)發(fā)布→生產(chǎn)發(fā)布。
需求評(píng)審時(shí),產(chǎn)品經(jīng)理必須把需求講清楚,開發(fā)人員有疑問當(dāng)場提出,避免后續(xù)返工。任務(wù)拆分用 Jira 來管理,每個(gè)任務(wù)細(xì)化到 2 - 4 小時(shí)能完成,這樣便于跟蹤進(jìn)度。代碼審查是關(guān)鍵環(huán)節(jié),我們用 GitLab 的 Merge Request 來做,規(guī)定必須至少有一個(gè)同事審核通過才能合并代碼,而且審查時(shí)不僅看代碼邏輯,還要看代碼規(guī)范、注釋是否清晰。
(二)「打破壁壘」的溝通技巧
在小團(tuán)隊(duì)里,跨部門溝通非常重要,尤其是和產(chǎn)品、運(yùn)營、測試的溝通。我們每周開一次站會(huì),每個(gè)人用三分鐘匯報(bào)自己的進(jìn)度、遇到的問題和需要的幫助。平時(shí)溝通盡量用企業(yè)微信或飛書,重要的事情一定要留痕,避免出現(xiàn)責(zé)任不清的情況。
和產(chǎn)品經(jīng)理溝通時(shí),要學(xué)會(huì)「擺事實(shí)講道理」,比如產(chǎn)品提出一個(gè)不合理的需求,不要直接拒絕,而是用技術(shù)數(shù)據(jù)說話,告訴他實(shí)現(xiàn)這個(gè)需求需要多少時(shí)間、會(huì)帶來哪些技術(shù)風(fēng)險(xiǎn),有沒有替代方案。和測試小姐姐溝通時(shí),要保持耐心,畢竟她們是幫我們發(fā)現(xiàn)問題的「眼睛」,遇到 bug 不要推諉,先認(rèn)真分析原因,及時(shí)修復(fù)。
(三)「自我成長」的獨(dú)門秘籍
在小公司,沒有人會(huì)手把手教你,全靠自己主動(dòng)學(xué)習(xí)。我每天都會(huì)留出半小時(shí)學(xué)習(xí)新技術(shù),通過博客、公眾號(hào)、技術(shù)論壇了解行業(yè)動(dòng)態(tài)。遇到不懂的問題,先自己查資料,百度、Stack Overflow 是我的好幫手,實(shí)在解決不了再請(qǐng)教同事或大佬。
我們還成立了「技術(shù)分享小組」,每周輪流分享技術(shù)知識(shí),有人分享最新的 Java 框架,有人分享數(shù)據(jù)庫優(yōu)化經(jīng)驗(yàn),有人分享前端開發(fā)技巧。通過分享,不僅能提升自己的表達(dá)能力,還能讓團(tuán)隊(duì)成員共同進(jìn)步。另外,我建議大家多參加線下技術(shù)沙龍,雖然小公司可能沒有大公司那樣的資源,但現(xiàn)在很多技術(shù)社區(qū)都有免費(fèi)的活動(dòng),去聽聽大佬們的分享,和同行交流交流,收獲很大。
四、避坑指南:小團(tuán)隊(duì)常見問題解決方案
(一)「祖?zhèn)鞔a」重構(gòu)策略
面對(duì)祖?zhèn)鞔a,千萬不要想著一口吃個(gè)胖子,直接全部重構(gòu),這樣風(fēng)險(xiǎn)太大,很可能導(dǎo)致系統(tǒng)崩潰。我們采用了「漸進(jìn)式重構(gòu)」策略,先梳理代碼結(jié)構(gòu),找出核心模塊和邊緣模塊,從邊緣模塊開始重構(gòu),比如先重構(gòu)那些不常用的工具類、舊的報(bào)表模塊。
在重構(gòu)過程中,一定要寫單元測試,保證重構(gòu)后的代碼功能不變。我們用 Mockito 來做單元測試,覆蓋主要的業(yè)務(wù)邏輯,這樣即使以后再修改代碼,也能通過單元測試快速驗(yàn)證。另外,重構(gòu)時(shí)要和團(tuán)隊(duì)成員溝通,避免重復(fù)勞動(dòng),比如我在重構(gòu)用戶中心時(shí),先在團(tuán)隊(duì)群里通知大家,讓其他依賴用戶中心的同事知道我的重構(gòu)計(jì)劃,避免他們?cè)谖抑貥?gòu)期間修改相關(guān)代碼。
(二)「突發(fā)流量」應(yīng)對(duì)方案
小公司的服務(wù)器配置一般不會(huì)太高,遇到突發(fā)流量很容易扛不住。比如有次做促銷活動(dòng),流量突然暴增,服務(wù)器直接卡死。后來我們總結(jié)經(jīng)驗(yàn),制定了一套應(yīng)對(duì)方案:
- 事前壓測:用 JMeter 對(duì)核心接口進(jìn)行壓測,找出性能瓶頸,提前優(yōu)化數(shù)據(jù)庫索引、增加緩存、調(diào)整 Tomcat 線程池參數(shù)。
- 流量分層:通過 Nginx 做負(fù)載均衡,把流量分發(fā)到多個(gè)服務(wù)器;用 Redis 做分布式 Session,避免用戶登錄狀態(tài)丟失;對(duì)靜態(tài)資源進(jìn)行 CDN 加速,減少服務(wù)器壓力。
- 熔斷降級(jí):通過 Hystrix 實(shí)現(xiàn)熔斷降級(jí),當(dāng)某個(gè)服務(wù)不可用或響應(yīng)超時(shí),直接返回友好的提示,避免級(jí)聯(lián)故障。
- 事后復(fù)盤:每次流量高峰過后,召開復(fù)盤會(huì)議,總結(jié)問題,優(yōu)化方案。
(三)「人員流失」應(yīng)急措施
小公司人員流動(dòng)性比較大,突然有同事離職,接手他的工作是個(gè)大問題。我們建立了「知識(shí)共享機(jī)制」,每個(gè)項(xiàng)目都有詳細(xì)的文檔,包括架構(gòu)設(shè)計(jì)、接口文檔、部署流程、常見問題解決方案等,這些文檔放在 Wiki 上,方便大家隨時(shí)查閱。
另外,我們實(shí)行「AB 角制度」,每個(gè)模塊至少有兩個(gè)人熟悉,A 同事負(fù)責(zé)主要開發(fā),B 同事作為備份,平時(shí)也參與該模塊的代碼審查和測試,這樣當(dāng) A 同事離職時(shí),B 同事能快速接手。我就曾經(jīng)作為 B 角,在 A 同事突然離職后,順利接手了訂單系統(tǒng)的維護(hù)和開發(fā)工作,雖然過程有點(diǎn)辛苦,但因?yàn)槠綍r(shí)有一定的了解,所以沒有出現(xiàn)太大的問題。
五、在小公司 IT 崗,我們到底在堅(jiān)持什么?
有人說,小公司 IT 崗就是個(gè)「坑」,學(xué)不到正規(guī)的技術(shù),發(fā)展前景有限。但我想說,正是在這樣的環(huán)境里,我們鍛煉了「十八般武藝」,從代碼編寫到架構(gòu)設(shè)計(jì),從團(tuán)隊(duì)協(xié)作到跨部門溝通,每一項(xiàng)技能都是在實(shí)戰(zhàn)中積累起來的。
在這里,我們見證了產(chǎn)品從 0 到 1 的誕生,看著自己寫的代碼每天被成千上萬的用戶使用,這種成就感是無法用言語表達(dá)的。雖然沒有大公司那樣完善的技術(shù)體系和豐富的資源,但我們有無限的創(chuàng)新空間,可以嘗試各種新技術(shù)、新方案,不用擔(dān)心因?yàn)榱鞒谭爆嵍鵁o法落地。
當(dāng)然,我們也不能一直「硬撐」,當(dāng)感覺自己的成長遇到瓶頸,公司的發(fā)展前景不明朗時(shí),也要勇敢地做出選擇。但在這之前,希望大家能珍惜在小公司的每一天,把每一次挑戰(zhàn)都當(dāng)作成長的機(jī)會(huì),努力提升自己的技術(shù)能力和綜合素質(zhì)。