<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          為什么阿里巴巴禁止使用存儲(chǔ)過程?

          共 2353字,需瀏覽 5分鐘

           ·

          2019-12-03 23:24


          f40ab106d63e7e44a4aa672178f67ba8.webp

          黑客技術(shù)點(diǎn)擊右側(cè)關(guān)注,了解黑客的世界!

          9fb32727d1b18bbf4920cf4a4469e52a.webp

          Java開發(fā)進(jìn)階點(diǎn)擊右側(cè)關(guān)注,掌握進(jìn)階之路!

          f72446241931d080ae16b3221e9f1005.webp

          Python開發(fā)點(diǎn)擊右側(cè)關(guān)注,探討技術(shù)話題!


          作者丨楊洋的圍脖啊?
          鏈接:segmentfault.com/a/1190000011138993

          6204981b8a83431959de8ca09c90486d.webp

          之所以有這個(gè)題目,我既不是故意吸引眼球,也不想在本文對(duì)存儲(chǔ)過程進(jìn)行教科書般論述。《阿里巴巴Java開發(fā)手冊(cè)》是這樣規(guī)定的:


          12b0878952864b1d1991d8e9ef89cc44.webp

          再結(jié)合我最近項(xiàng)目中遇到的存儲(chǔ)過程問題,所以今天我打算來(lái)聊一聊這個(gè)問題。

          這事兒要從去年在武漢出差時(shí)一位同事的發(fā)問說(shuō)起,問題是這樣的:

          我覺得存儲(chǔ)過程挺好用的,你為什么不建議用呢?

          當(dāng)時(shí)我好似胸有萬(wàn)言,但終究沒用一個(gè)實(shí)在的例子回答同事,只是從結(jié)論上大侃一通,代碼相對(duì)于SQL,復(fù)用、擴(kuò)展、通用性都要更強(qiáng)。想必同事并不信服。

          現(xiàn)在想來(lái),我最近正碰到的問題,算是一個(gè)可以回答同事的例子吧。

          最近項(xiàng)目中有個(gè)新需求,需要校驗(yàn)一個(gè)用戶是否有Job,Certification,Disclosure這三個(gè)業(yè)務(wù)數(shù)據(jù)。

          翻看了代碼發(fā)現(xiàn),系統(tǒng)的用戶個(gè)人頁(yè)面的C#代碼調(diào)用了三個(gè)存儲(chǔ)過程,去抓取用戶的Job,Certification,Disclosure數(shù)據(jù)。

          我的新需求,自然需要復(fù)用這三個(gè)存儲(chǔ)過程,否則:

          若每一處都寫一次抓取數(shù)據(jù)的業(yè)務(wù)邏輯代碼,若業(yè)務(wù)邏輯發(fā)生變化,難以追查和維護(hù)所有讀取Job,Certification,Disclosure的SQL。

          如果我在C#代碼中調(diào)用這已有的三個(gè)存儲(chǔ)過程,事情本該非常快就能結(jié)束。我也是這么做的。

          但code reviewer認(rèn)為,我的需求中,并不需要Job,Certification,Disclosure這三個(gè)業(yè)務(wù)對(duì)象的數(shù)據(jù)。我只是需要給定用戶是否有Job,Certification,Disclosure而已。所以我應(yīng)將是否有無(wú)Job,Certification,Disclosure的判斷邏輯寫在數(shù)據(jù)庫(kù),最終通過網(wǎng)絡(luò)從數(shù)據(jù)庫(kù)傳到web服務(wù)器的僅是true或false,節(jié)省網(wǎng)絡(luò)流量,這樣最好不過了。

          也對(duì)。除開網(wǎng)絡(luò)性能,從接口設(shè)計(jì)的角度講,接口的傳入和返回值,都應(yīng)是你本身需要的數(shù)據(jù),不應(yīng)帶有大量不需要或者需要caller去預(yù)處理的數(shù)據(jù)。從接口語(yǔ)義表達(dá)就可知調(diào)用的目的,這樣代碼可讀性也會(huì)有大大提高。

          那就動(dòng)手改。但沒想到的是問題來(lái)了。

          為了講述問題,我簡(jiǎn)化代碼,假設(shè)系統(tǒng)現(xiàn)有的存儲(chǔ)過程如下:


          CREATE PROCEDURE [dbo].[GetJobs]
          (
          @PersonId int,
          @OrganizaitionId int
          )
          AS
          BEGIN
          SELECT JobId,JobName,JobType FROM Job WHERE PersonId = @PersonId AND OrganizaitionId = @OrganizaitionId
          END

          我在新的存儲(chǔ)過程中調(diào)用它,我需要獲得該person的jobs的數(shù)量,即GetJobs返回結(jié)果集的count。

          為了實(shí)現(xiàn)這一目的,首先想到的是使用臨時(shí)表,將返回結(jié)果集存入臨時(shí)表,再對(duì)其進(jìn)行count(*)的計(jì)數(shù)操作:

          CREATE PROCEDURE [dbo].[MyProc]
          (
          @PersonId int,
          @OrganizaitionId int,
          )
          AS
          BEGIN
          CREATE TABLE #Temp(
          PersonId int,
          OrganizaitionId int
          )

          INSERT INTO #Temp EXEC dbo.GetJobs
          @PersonId = @PersonId,
          @ParentOrgId = @ParentOrgId

          SELECT COUNT(*) FROM #Temp
          END

          這種辦法簡(jiǎn)單有效,但它存在嚴(yán)重的維護(hù)問題。未來(lái)如果被調(diào)用的存儲(chǔ)過程的返回結(jié)果集字段有變動(dòng),那么MyProc中的臨時(shí)表結(jié)構(gòu)也需要隨之變化。這是令人難以接受的。

          那么將MyProc中的INSERT INTO換為SELECT INTO呢?很遺憾,答案是不行。SQL本身并不支持這種用法。

          給現(xiàn)有存儲(chǔ)過程GetJobs加output參數(shù)?本例中因?yàn)镚etJobs已被其他多處代碼或SQL scripts調(diào)用,所以對(duì)現(xiàn)有現(xiàn)有存儲(chǔ)過程進(jìn)行改動(dòng)會(huì)有不小風(fēng)險(xiǎn)。

          我搜遍網(wǎng)絡(luò),一位MS MVP的大神的文章幾乎總結(jié)了所有存儲(chǔ)過程之間傳遞數(shù)據(jù)的方法: How to Share Data between Stored Procedures。他在文章中也無(wú)可奈何地說(shuō)道

          Keep in mind that compared to languages such as C# and Java, Transact-SQL is poorly equipped for code reuse, why solutions in T?SQL to reuse code are clumsier.

          最終我沒能找到一種滿意的辦法,無(wú)奈之下我在新寫的存儲(chǔ)過程中將查詢Jobs的語(yǔ)句寫一了次。

          存儲(chǔ)過程在很多場(chǎng)景時(shí)有其優(yōu)勢(shì),比如性能。但對(duì)于業(yè)務(wù)邏輯的通用方法,非常不推薦將其寫在存儲(chǔ)過程中,代碼復(fù)用、擴(kuò)展與客戶端語(yǔ)言比,相差甚遠(yuǎn)。也許終究能實(shí)現(xiàn),但代價(jià)與風(fēng)險(xiǎn)比客戶端語(yǔ)言要高,得不償失。

          天知道還有沒有機(jī)會(huì)和那位前同事再討論這一話題呢。


          ?推薦↓↓↓?

          長(zhǎng)

          關(guān)

          ?16個(gè)技術(shù)公眾號(hào)】都在這里!

          涵蓋:程序員大咖、源碼共讀、程序員共讀、數(shù)據(jù)結(jié)構(gòu)與算法、黑客技術(shù)和網(wǎng)絡(luò)安全、大數(shù)據(jù)科技、編程前端、Java、Python、Web編程開發(fā)、Android、iOS開發(fā)、Linux、數(shù)據(jù)庫(kù)研發(fā)、幽默程序員等。

          319eed55d1a8cbbed742c53df962f7b7.webp萬(wàn)水千山總是情,點(diǎn)個(gè) “在看” 行不行
          瀏覽 68
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  91麻豆亚洲国产成人久久精品 | 免费日逼无码大片 | 亚洲精品成人7777777 | 看欧美黄色片 | 狼友在线播放 |