您的網站不應該只提供一套通用 API

后端應該提供兩套 API,一套是外部使用的通用 API,服務特定的數據,另一套是自家使用的應用 API,服務特定的頁面。

在當今的web開發中,構建一個提供JSON服務的后端和一個渲染應用程序的前端是很流行的。我不太喜歡,但還好。但是如果你認為你的后端需要被設計成一個通用的公共API是不行的。這不會節省你的時間。

為什么不喜歡呢?

當你設計一個通用API時,你必須弄清楚一堆煩人的東西。

  1. 如何預測和啟用所有可能的工作流
  2. 如何避免N+1請求的尷尬工作流程
  3. 如何測試每個可能的請求的功能、性能和安全性
  4. 如何在不破壞現有工作流的情況下更改API
  5. 如何在內部需求和公共需求之間確定API變更的優先級
  6. 如何記錄每件事,以便各方都能完成工作

在前端,還有很多:

  1. 如何收集呈現頁面所需的所有數據
  2. 如何優化對多個端點的請求
  3. 如何避免以非預期的方式使用API數據字段
  4. 如何權衡新功能的好處和新API請求的成本

如果你只是為前端制作后端,這些真的是你的問題嗎?你是否必須想象每一個可能的工作流程,避免N+1請求問題,測試每個請求配置,或者在確切知道每個頁面應該是什么樣子的情況下拒絕使用自己的功能?你們可以看出我的意思。

那有什么建議呢

我建議你不要再把你的前端當成一些通用的API客戶端,而是把它當成你應用的一半。
想象一下,如果你可以將整個“page”的JSON值發送給它。為/page/a創建一個端點,并在那里渲染/page/a的整個JSON。對每一頁都這樣做。不要強迫你的前端開發人員發送一堆單獨的請求來渲染復雜的頁面。不要用人為的限制來煩他們。
在那個JSON中,實際渲染頁面。不要渲染抽象的模型和集合。渲染具體的框、節、段落、列表。渲染可視化頁面結構。

{"section1": {"topBoxTitle": "Foo","leftBoxTitle": "Bar","linkToClose": "https://…"},"section2": {…}
}

這與服務器驅動的UI類似但不完全相同。也許我們可以稱它為服務器通知的UI。

怎么做會更好呢?

你見過上面那些煩人的決定嗎?首先,他們現在已經走了。
其次,你現在可以自由決定“我想要頁面 a”,然后在后端和前端實現“頁面 a”。超級簡單。
不再有“我們需要引入什么API工作流才能讓這個頁面幾乎成為可能?”。你可以讓“頁面 a”保持沉默,只做它需要做的事情。你把“第一頁”的漏洞,安全性,性能都測試了個遍。你甚至可以在一個簡單的SQL查詢中獲取“頁面a”的所有內容。你可以緩存“頁面 a”的整個JSON負載。
前端確切地知道“頁面 a”有效載荷中的每個字段的用途。在字段含義上沒有差異。它們完全代表了前端的需求。
當項目干系人告訴你修改“頁面a”時,你可以直接修改“頁面a”,而不是花很多時間來弄清楚后端API如何適應“頁面a”的更改。它不是API請求編排的集合。只是“第1頁”。你已經將自己從自己強加的API限制中解放出來。

您的業務邏輯現在已經從隨意地在前端和后端之間劃分為僅后端。你的前端終于可以專注于表現和UI了。你的后端最終可以專注于實現所需的功能。有點像目標,不是嗎?

你真的試過這個嗎

是的,到目前為止,我已經在幾個生產項目中嘗試過這種方法。其中一個是個人原因,另一個是在現有公司中持續多年的重構工作。整個團隊都被說服了,結果很好。我們遇到的唯一問題是前端團隊變得越來越無聊。幾乎所有的業務邏輯都被剝奪了。與此同時,后端團隊并沒有感到“興奮”。一切都變得有點無聊。不知怎么的,我們最終都討論了更多的業務而不是代碼。
如果你被說服了,請隨時停止閱讀。下一部分是對我不斷聽到的各種反駁的回應。

但我希望我的前端團隊有自由!(或者我希望我的前端解耦!)

老實說,你的前端沒有自由。當他們向你發送7個請求來渲染一個頁面時,這不是自由。這是為了滿足基本要求而跳的。一旦需求改變,您可能需要改變后端來適應它。自由都是偶然的,而且大多是在錯誤的地方。
如果你真的想給予你的前端團隊自由,直接在Postgres上安裝GraphQL包裝器,然后退出。

但我們實際上想要一個通用API,所以這是一石二鳥,不是嗎?

不,您實際上并不希望將此API公開。你以為你會,但到了時候,你會說“糟了,也許我不應該”。這兩個API有非常不同的原因來改變。公共API需要啟用客戶端的工作流。私有后端需要啟用您的產品經理的下一個心血來潮。別再把棍子塞進你自己的自行車輪子里了。

但是在為頁面構建JSON時,我將如何重用邏輯呢?我在我的CRUD控制器中重用了這么多邏輯!

如果你的編程語言允許重用邏輯(它確實如此),那么你就可以重用邏輯。使用合成,繼承,任何你需要使用的東西。如果你自己做了一些好的抽象,那么你將有一個驚人的時間從你的樂高積木組合在一起頁面。

但我們也可以將此API重用到移動的應用程序中!

您的移動的應用程序有一組不同的頁面,其中包含不同的信息、結構和更改原因。您將保存更多的時間和理智為它制作另一個后端專門。但是,嘿,你可以重用很多邏輯(見上一段)。

但是,如果頁面需要部分XHR更新怎么辦?我總是要返回一整頁嗎?

不,創建一個只返回特定內容的端點是可以的。我允許你去。為特定頁面部分的數據片段創建端點或其他內容。沒事了,我沒事了從初始負載渲染React組件,然后通過XHR調用對這些端點進行更新。但只有在某些頁面上需要它們時才引入這些端點。這些都是例外情況,而不是默認情況。

但是我的前端是SPA,所以它幾乎總是需要數據片段,而不是整個頁面

這些數據片段仍然可以作為部分頁面結構而不是通用資源來提供。只要你的后端只服務于前端的確切需求,你就很好。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/36291.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/36291.shtml
英文地址,請注明出處:http://en.pswp.cn/news/36291.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

【Sklearn】基于決策樹算法的數據分類預測(Excel可直接替換數據)

【Sklearn】基于決策樹算法的數據分類預測(Excel可直接替換數據) 1.模型原理1.1 模型原理1.2 數學模型 2.模型參數3.文件結構4.Excel數據5.下載地址6.完整代碼7.運行結果 1.模型原理 決策樹是一種基于樹狀結構的分類和回歸模型,它通過一系列…

MySql(干貨)

寫這篇博客的目的不是為了將介紹原理,而是為了Sql中的代碼操作屬實太多了,在這里進行一個匯總,方便查閱!!! Sql分類 分類全稱說明 DDL Data Definintion Language數據定義語言,用來定義數據庫對…

微信小程序(由淺到深)

文章目錄 一. 項目基本配置1. 項目組成2. 常見的配置文件解析3. app.json全局的五大配置4.單個頁面中的page配置5. App函數6.tabBar配置 二. 基本語法,事件,單位1. 語法2. 事件3. 單位 三. 數據響應式修改四 . 內置組件1. button2. image3. input4. 組件…

k8s常用資源管理 控制

目錄 Pod(容器組):Pod是Kubernetes中最小的部署單元,可以包含一個或多個容器。Pod提供了一種邏輯上的封裝,使得容器可以一起共享網絡和存儲資源 1、創建一個pod 2、pod管理 pod操作 目錄 創建Pod會很慢 Pod&…

什么是事務,并發帶來的事務問題以及事務隔離級別(圖文詳解)

一、什么是事務? 簡單說就是邏輯上的一組操作,要么都執行,要么都不執行。 舉個例子,假如小明要給小紅轉賬100元,這個轉賬會涉及到兩個關鍵操作:①將小明的余額減少100元。 ②將小紅的余額增加100元 。但…

學習筆記整理-JS-04-流程控制語句

文章目錄 一、條件語句1. if語句的基本使用2. if else if多條件分支3. if語句算法題4. switch語句5. 三元運算符 二、循環語句1. for循環語句2. for循環算法題3. while循環語句4. break和continue5. do while語句 三、初識算法1. 什么是算法2. 累加器和累乘器3. 窮舉法4. 綜合算…

給大家推薦一些文本翻譯、文檔翻譯API接口

最近在項目中要接入文本翻譯和文檔翻譯功能,滿足在工作時使用,又需要了解每個人的使用情況,所以采用了集成翻譯API的方式,我再調研時也查了比較多的資料,總結了我感覺比較好的網站。 推薦網站 1、百度翻譯&#xff0…

設計模式(2)工廠方法模式

一、 1、介紹:定義一個用于創建對象的接口,讓子類決定實例化哪一個類。工廠方法使一個類的實例化延遲到其子類。簡單工廠模式的最大優點在于工廠類中包含了必要的邏輯判斷,根據客戶端的選擇條件動態實例化相關的類,對于客戶端來說…

odoo-034 float 浮點數比較

文章目錄 前提問題解決總結 前提 odoo 版本:13 python:3.6.9 問題 比較銷售訂單行中已送貨跟已開票,在 tree 視圖顯示搜索后的結果。發現搜索條件為已送貨 > 已開票時,結果中會包含已送貨已開票的。 解決 把這兩個值打印出…

LeNet中文翻譯

Gradient-Based Learning Applied to Document Recognition 基于梯度的學習應用于文檔識別 摘要 使用反向傳播算法訓練的多層神經網絡構成了成功的基于梯度的學習技術的最佳示例。給定適當的網絡架構,基于梯度的學習算法可用于合成復雜的決策表面,該決策…

【Vue-Router】使用 prams 路由傳參失效

報錯信息: [Vue Router warn]: Discarded invalid param(s) “name”, “price”, “id” when navigating. list.json {"data": [{"name": "面","price":300,"id": 1},{"name": "水",&quo…

node獲取微信小程序登錄用戶的openid

前提準備: 1、需要知道AppID(小程序ID) 2、AppSecret(小程序密鑰) 3、調wx.login成功后返回的code 代碼如下: const express require(express); const router express.Router(); const request require(request) const APP_URL https://api.wei…

考研408 | 【計算機網絡】 網絡層

導圖 網絡層: 路由器功能:轉發&路由選擇 數據平面 數據平面執行的主要功能是根據轉發表進行轉發,這是路由器的本地動作。 控制平面 1.傳統方法/每路由器法: 2.SDN方法(Software-Defined Networking) 控制平面中的…

C++并發多線程--多個線程的數據共享和保護

目錄 1--創建并等待多個線程 2--數據共享 2-1--數據只讀 2-2--數據讀寫 2-3--共享數據保護簡單案例 1--創建并等待多個線程 創建多個線程時,可以使用同一個線程入口函數; 多個線程的執行順序與操作系統的調度機制有關,并不和創建線程的先…

html實現商品圖片放大鏡,html圖片放大鏡預覽

效果 實現 復制粘貼&#xff0c;修改圖片路徑即可使用 <!DOCTYPE html> <html><head><meta charset"UTF-8"><title>商品圖片放大鏡</title></head><style>body {margin: 0;padding: 0;}#app {padding: 10px;posit…

關于青少年學習演講與口才對未來的領導力的塑造的探析

標題&#xff1a;青少年學習演講與口才對未來領導力的塑造&#xff1a;一項探析 摘要&#xff1a; 本論文旨在探討青少年學習演講與口才對未來領導力的塑造的重要性和影響。通過分析演講和口才對青少年的益處&#xff0c;以及如何培養這些技能來促進領導力的發展&#xff0c;我…

Harmony創建項目ohpm報錯

Harmony創建FA模型的項目時報如下錯&#xff1a; The registry is empty - edit .ohpmrc file or use "ohpm config set registry your_registry" command to set registry.解決方法&#xff1a; File -> Settings -> Build,Execution,Deployment -> Ohpm …

機器學習基礎(五)

決策樹 決策樹是一種預測模型,它代表著對象屬屬性與對象值之間的一種映射關系。樹中的每個節點代表一個對象,分叉路徑(或者叫樹枝)則代表一個屬性值。 決策樹常用方法: 分類樹分析,是一種監督學習,用于預計結果可能為離散類型。 回歸樹分析,用于預計結果為實數。 CART,…

Mysql事務及其隔離機制/隔離級別

mysql事務特性是什么&#xff1f; 原子性(atomicity)&#xff1a;一個事務必須視為一個不可分割的最小工作單元&#xff0c;整個事務中的所有操作要么全部提交成功&#xff0c;要么全部失敗回滾&#xff0c;對于一個事務來說&#xff0c;不可能只執行其中的一部分操作&#xf…

docker可視化工具Portainer

1:Portainer簡介 Portainer是一個docker可視化管理工具&#xff0c;可以非常方便地管理docker鏡像容器。官網地址&#xff1a;https://www.portainer.io/ 注&#xff1a;現在Portainer有BE&#xff08;收費&#xff09;和CE&#xff08;免費&#xff09;版本&#xff0c;安裝的…