返回

Java面試題| 框架篇

1:SSH框架

(1)SSH三大框架的概述

SSH為 struts+spring+hibernate的一個集成框架,是目前較流行的一種Web應用程序開源框架。

集成SSH框架的系統從職責上分為四層:表示層、業務邏輯層、數據持久層和域模塊層(實體層),以幫助開發人員在短期內搭建結構清晰、可復用性好、維護方便的Web應用程序。

struts標簽庫:Struts2默認的表達式語言是OGNL(Object-Graph Navigation Language),通過它可以存取對象的任意屬性、調用對象的方法、遍歷整個對象的結構圖、實現字段類型轉換等功能。

JSP: HTML文件中插入Java程序段和JSP標記。

web.xml: Struts2核心過濾器和監聽器

struts.xml: 管理應用中的Action映射,及Action處理結果和物理資源之間的映射。

applicationContext.xml: 整合了struts和Hibernate。

.hbm.xml:O/R Mapping(Object Relational Mapping)映射文件,實體和表的映射關系通過XML來描述的文件。在項目啟動的時候加載到內存中。

PO:Persistent Object,持久化對象

整體的調用關系:JSP–Action–Service–DAO–PO–數據庫

(2)什么是struts2

Struts2是一個基于MVC設計模式的Web應用控制層框架,功能就是完成jsp頁面和后臺java代碼的傳值和跳轉。

Struts2的運行原理

1:當前臺發送一個以規定后綴相同的請求時 如:.action struts核心控制器會對其進行過濾攔截 核心控制器StrutsPrepareAndExecuteFilter

2:核心控制器攔截請求后會根據請求的路徑找到對應的java代碼,通過路徑中的類名(!前的部分)匹配struts.xml中action標簽中的name屬性來找到具體訪問的類,!后的部分匹配類中的方法名

3:當java類中完成處理邏輯會返回一個字符串,根據字符串匹配struts.xml中result標簽的name屬性,然后跳轉到result標簽內容指定的頁面。

(3)Spring

簡單來說,spring是一個輕量級的控制反轉(IOC)和面向切面(AOP)的容器框架。

◆ 輕量——從大小與開銷兩方面而言Spring都是輕量的。完整的Spring框架可以在一個大小只有1MB多的JAR文件里發布。并且Spring所需的 處理開銷也是微不足道的。此外,Spring是非侵入式的:典型地, Spring應用中的對象不依賴于Spring的特定類。

◆ 控制反轉——Spring通過一種稱作控制反轉(IOC)的技術促進了松 耦合。當應用了IOC,一個對象依賴的其它對象會通過被動的方式傳遞 進來,而不是這個對象自己創建或者查找依賴對象。這也是說spring是非侵入式的,動態注入對象,讓一個對象的創建 不用new,可以自動生成,這就是利用JAVA里的反射,反射其實就是 在運行時動態的去創建、調用對象及其方法,spring就是在運行時,跟 xml spring的配置文件來動態的創建對象,和調用對象里面的方法 反射技術的使用使得我們不再像原始的工廠方法模式那樣創建對象。反 射可以非常靈活的根據類的名稱創建一個對象。所以spring只使用了 Prototype和Singleton這兩個基本的模式。

◆ 面向切面——Spring提供了面向切面編程的豐富支持,允許通過分離 應用的業務邏輯與系統級服務(例如審計(auditing)和事務 (transaction)管理,主要實現對事務的管理)進行內聚性的開發,其 機理來自于代理模式。應用對象只實現它們應該做的——完成業務邏輯 ——僅此而已。它們并不負責(甚至是意識)其它的系統級關注點,例 如日志或事務支持。

◆ 容器——Spring包含并管理應用對象的配置和生命周期,在這個意義上它是一種容器,你可以配置你的每個bean如何被創建——基于一個可配置原型(prototype),你的bean可以創建一個單獨的實例或者每次需要時都生成一個新的實例——以及它們是如何相互關聯的。然而,Spring不應該被混同于傳統的重量級的EJB容器,它們經常是龐大與笨重的,難以使用。Spring是一個容器,凡是在容器里的對象才會有Spring所提供的這些服務和功能。凡是在spring的配置文件里面配置了,才能被spring管理;并享用spring提供的服務 。

◆ 框架——Spring可以將簡單的組件配置、組合成為復雜的應用。在Spring中,應用對象被聲明式地組合,典型地是在一個XML文件里。Spring也提供了很多基礎功能(事務管理、持久化框架集成等等),將應用邏輯的開發留給了你。所有Spring的這些特征使你能夠編寫更干凈、更可管理、并且更易于測試的代碼。它們也為Spring中的各種模塊提供了基礎支持。

談Spring這個問題的時候,首先Spring中最為重要的無非就是IOC和AOP,而對IOC來講,你講一下IOC的定義,IOC就是說對象本身的創建不依賴應用本身,而是依賴于外部容器,如果沒有IOC那么我們在我們的業務類,要調用DAO的方法,那么不得不做的一個動作就是創建一個DAO的實現類的實例,而創建這個對象本身是跟業務無關的,而這樣違反了“高內聚,低耦合”,使類與類的聯系非常緊密了。即使你不用new,你使用工廠模式,使用單利模式,也跟上面說的效果是一樣的,而Spring本身就是一個大工廠,他幫我們造對象,幫我們管理bean對象,它幫我們注入我們所需的bean對象,這樣對于以后的維護來講,變的更為方便,也把與業務本身無關的東西提取出來了。體現了低耦合。而AOP本身就是一種思想,意為面向切面編程,而Spring對AOP做了部分實現,(舉例說明)如果沒有AOP,比如我們開發的系統中有發郵件,寫日志,可想而知,系統中發郵件,寫日志絕對的不是在一個地方用到,那么怎么辦,肯定是在業務中寫著重復的代碼,而且干著與業務無關的事情,也就是說讓發郵件,寫日志跟業務一起混合在一起,那么這樣肯定是不合理的。那么該怎么辦,因此Spring提供了AOP,在你想寫日志的方法給你切開,加入日志的操作,剛剛說spring是大工廠,那么對于spring的AOP來講,我更加喜歡把它比喻成化妝師,只有你讓spring幫你化妝,就能達到你意想不到的效果,總的來講spring的AOP技術,他幫我們做很多與業務無關的操作,讓業務層次更加清晰。

Spring AOP事務的描述:

在applicationContent.xml里通過aop:config里面先設定一個表達式,設定對service里那些方法 如:對add* ,delete*,update*等開頭的方法進行事務攔截。我們需要配置事務的傳播(propagation=“REQUIRED”)特性,通常把增,刪,改以外的操作需要配置成只讀事務(read-only=“true”).只讀事務可以提高性能。之后引入tx:advice,在tx:advice引用 transactionManager(事務管理),在事務管理里再引入sessionFactory,sessionFactory注入 dataSource,最后通過aop:config引入txAdvice。

事物的7種傳播特性

opropagation_requierd:如果當前沒有事務,就新建一個事務,如果已存在一個事務中,加入到這個事務中,這是最常見的選擇。

opropagation_supports:支持當前事務,如果沒有當前事務,就以非事務方法執行。

opropagation_mandatory:使用當前事務,如果沒有當前事務,就拋出異常。

opropagation_required_new:新建事務,如果當前存在事務,把當前事務掛起。

opropagation_not_supported:以非事務方式執行操作,如果當前存在事務,就把當前事務掛起。

opropagation_never:以非事務方式執行操作,如果當前事務存在則拋出異常。

opropagation_nested:如果當前存在事務,則在嵌套事務內執行。如果當前沒有事務,則執行與propagation_required類似的操作

Spring默認的事物傳播行為是propagation_requierd

(4)Hibernate

1:hibernate 是什么

Hibernate是一個開放源代碼的對象關系映射框架,它對JDBC進行了非常輕量級的對象封裝,它將POJO與數據庫表建立映射關系,是一個全自動的orm框架,hibernate可以自動生成SQL語句,自動執行,使得Java程序員可以隨心所欲的使用對象編程思維來操縱數據庫。Hibernate可以應用在任何使用JDBC的場合

是基于JDBC使用面向對象封裝而來的 ORM 持久層框架/數據庫中間件

2:什么是ORM?

O :Object : 對象,

R :Relation : 關系型數據庫;-->oracle , mysql ,

M :Mapping : 映射 ;就是一個 xml 的配置文件,

通過配置文件將對象和關系型數據庫連接起來實現我們通過操作對象的形式來操作數據庫。

3:hibernate和jdbc的區別

1.jdbc和hibernate都是 數據庫中間件/持久層框架 用來操作數據庫

2.hibernate 是基于 jdbc封裝而來

不同

JDBC

1.不能跨數據庫 不同的數據庫使用不同鏈接驅動jar包

2.使用sql 語句操作數據庫

3.查詢時 結果集需要手動遍歷封裝到java對象

4.執行效率高 開發效率低

Hibernate

1.能夸數據庫 通過方言配置可以切換不同的數據庫語言

2.通過對象操作數據庫 或者是HQL語句不管是通過對象還是HQL語句最終都會變成sql語句執行

3.查詢時hibernate通過配置的關系 直接返回java對象通過反射機制自動封裝對象,反射是很耗費資源的

4.執行效率低 開發效率高

4:Hibernate核心類

Configuration 代表hibernate配置信息的類

hibernate啟動時通過Configuration類讀取數據庫配置和映射關系

configure()方法加載配置文件

buildSessionFactory()構建session工廠

SessionFactory 會話工廠 可以認為 是jdbc 中的Connection對象openSession()打開一個回話

Session會話類

操作數據庫的

save(對象) 新增

get(類型,主鍵) 只返回一條數據 必須根據主鍵查詢

load(類型,主鍵)只返回一條數據 必須根據主鍵查詢

delete(對象) 根據對象的id 刪除記錄

update(對象)根據對象的id修改記錄

saveOrUpdate(對象) 對象id不存在 執行新增 存在執行修改

Transaction 事務

transaction.commit();提交事務

transaction.rollback();回滾事務

Query書寫 執行 HQL語句

獲得 query

session.cre=ateQuery(“hql 可以有占位符號”);

1.替換占位符號

query.setParamenter(“下標從零開始,值”);

2.查詢 List結果集

query.list(); 返回多條數據 以List集合的形式

3.獲得唯一結果集(必須確定結果集唯一才能使用)

uniqueResult(); 只返回一個Object對象

4.執行修改數據的操作

executeUpdate(); 執行刪除 新增 修改的 語句

5:主鍵生成策略

increment:適用于short,int,long作為主鍵 ,不是使用的數據庫自動增長,是先查詢數據庫中最大 的id值,然后在最大的基礎上加一,然后賦值 。

identity :自動遞增,只適用于自動遞增的數據庫。(oracle不能使用)。

sequence:序列,只適用于有序列的數據庫。(適用與oracle)。

uuid:適用于char,varchar類型的主鍵。

native:本地的。使用數據庫本身的方式,

(比如oracle是使用序列,而mysql則使用遞增)。

6:Hibernate緩存

緩存是介于應用程序和物理數據源之間,其作用是為了降低應用程序對物理數據源訪問的頻次,從而提高了應用的運行性能。

緩存內的數據是對物理數據源中的數據的復制,應用程序在運行時從緩存讀寫數據,在特定的時刻或事件會同步緩存和物理數據源的數據。

一級緩存 自動開啟的 是session的緩存 無需配置 自動使用

二級緩存 是需要配置 第三方緩存 例如 OScache 是sessionFactory 的緩存

三級緩存/查詢緩存 無需配置 自動使用

7:Hibernate查詢的策略

是先從緩存查詢對象如果緩存中沒有對應條件的對象再發送sql語句查詢數據庫,如果緩存中存在符合條件的對象就是用緩存中的數據,從而降低查詢效率。

8:get和load的區別

1.get 當查詢的id 在緩存和數據庫中都不存在的話 返回 null

2.load 當查詢的id 在緩存和數據庫中都不存在的話會發生異常 ObjectNotFoundException

load 可以執行 懶加載的操作

懶加載功能: 當我們查詢一個 hibernate對象時只獲得對象的id

當使用到對象的其他屬性時再去數據庫查詢其他的信息

9:Hibernate對象狀態

Hibernate中對象有三種狀態:臨時狀態(Transient)、持久狀態(Persistent)、游離狀態(Detached)。

臨時狀態:剛剛使用new語句創建,還沒有被持久化,不處于Session的緩存中。處于臨時狀態的狀態的Java對象被稱為臨時對象。

持久化狀態:已經被持久化,加入到Session的緩存中。處于持久化狀態的Java對象被稱為持久化對象。

游離狀態/托管狀態:已經被持久化,但不處于session的緩存中。處于游離狀態的Java對象被稱為游離對象。

10:為什么使用hibernate

1)、對JDBC訪問數據庫的代碼做了封裝,大大簡化了數據訪問層繁瑣的重復性代碼。

2)、Hibernate是一個優秀的ORM實現。他很大程度的簡化DAO層的編碼工作,將軟件開發人員從大量相同的數據持久層相關編程工作中解放出來,使開發更對象化了。

3)、移植性好,支持各種數據庫,如果換個數據庫只要在配置文件中變換配置就可以了,不用改變hibernate代碼。

4)、支持透明持久化,因為hibernate操作的是純粹的(pojo)java類,沒有實現任何接口,沒有侵入性。所以說它是一個輕量級框架。

11:談談你對Hibernate的理解。

  1. 面向對象設計的軟件內部運行過程可以理解成就是在不斷創建各種新對象、建立對象之間的關系,調用對象的方法來改變各個對象的狀態和對象消亡的過程,不管程序運行的過程和操作怎么樣,本質上都是要得到一個結果,程序上一個時刻和下一個時刻的運行結果的差異就表現在內存中的對象狀態發生了變化。
  2. 2.為了在關機和內存空間不夠的狀況下,保持程序的運行狀態,需要將內存中的對象狀態保存到持久化設備和從持久化設備中恢復出對象的狀態,通常都是保存到關系數據庫來保存大量對象信息。從Java程序的運行功能上來講,保存對象狀態的功能相比系統運行的其他功能來說,應該是一個很不起眼的附屬功能,java采用jdbc來實現這個功能,這個不起眼的功能卻要編寫大量的代碼,而做的事情僅僅是保存對象和恢復對象,并且那些大量的jdbc代碼并沒有什么技術含量,基本上是采用一套例行公事的標準代碼模板來編寫,是一種苦活和重復性的工作。
  3. 3.通過數據庫保存java程序運行時產生的對象和恢復對象,其實就是實現了java對象與關系數據庫記錄的映射關系,稱為ORM(即Object Relation Mapping),人們可以通過封裝JDBC代碼來實現了這種功能,封裝出來的產品稱之為ORM框架,Hibernate就是其中的一種流行ORM框架。使用Hibernate框架,不用寫JDBC代碼,僅僅是調用一個save方法,就可以將對象保存到關系數據庫中,僅僅是調用一個get方法,就可以從數據庫中加載出一個對象。
  4. 4.使用Hibernate的基本流程是:配置Configuration對象、產生SessionFactory、創建session對象,啟動事務,完成CRUD操作,提交事務,關閉session。
  5. 5.使用Hibernate時,先要配置hibernate.cfg.xml文件,其中配置數據庫連接信息和方言等,還要為每個實體配置相應的hbm.xml文件,hibernate.cfg.xml文件中需要登記每個hbm.xml文件。
  6. 6.在應用Hibernate時,重點要了解Session的緩存原理,級聯,延遲加載和hql查詢。
  7. (5)SSH整合
  8. 在項目中首先是通過在web.xml中配置strtus2的前端控制器StrutsPrepareAndExecuteFilter加載struts.xml
  9. 配置文件并對指定的后綴名進行攔截,并且通過配置spring的監聽器contextLoadListener
  10. 加載spring的相關配置文件如
  11. spring-service.xml,spring-dao.xml,spring-common.xml,
  12. 之后新建控制層的類繼承于BaseAction,而BaseAction繼承于ActionSupport,
  13. 在BaseAction中封裝了常用的方法如getRealPath(),outJson()等,
  14. 之后控制層注入service層,service層注入dao,dao層繼承于HibernateDaoSupport
  15. 并注入spring-common.xml中配置的sessionFactory,sessionFactory注入dataSource連接數據庫,
  16. 注入hibernate.cfg.xml從而加載hbm.xml文件,
  17. 除此之外還通過Spring中的Aop配置了事務并且通過切點表達式對Servcie層代碼進行控制。
  18. (6)總結
  19. 在SSH中使用Struts作為系統的整體基礎架構,負責MVC的分離,在Struts框架的模型部分,控制業務跳轉,利用Hibernate框架對持久層提供支持,Spring做支持,支持struts和hibernate。具體做法是:用面向對象的分析方法根據需求提出一些模型,將這些模型實現為基本的Java對象,然后編寫基本的DAO(Data Access Objects)接口,并給出Hibernate的DAO實現,采用Hibernate架構實現的DAO類來實現Java類與數據庫之間的轉換和訪問,最后由Spring做支持,支持struts和hibernate。其實ssh框架最主要的本質是:“高內聚、低耦合”。
  20. SSH框架優點:
  21. 1.spring管理對象的實例化,把對象的創建和獲取放到外部,更加的靈活方便。
  22. 2.Hibernate避免了JDBC連接數據庫的冗余繁雜。
  23. 3.各層分工明細,實現了各層之間的解耦,代碼更加靈活。

2:SSM框架

(1)SSM框架概述

SSM框架是spring MVC ,spring和mybatis框架的整合,是標準的MVC模式,將整個系統劃分為表現層,controller層,service層,DAO層四層

使用spring MVC負責請求的轉發和視圖管理

spring實現業務對象管理,mybatis作為數據對象的持久化引擎

(2)SpringMVC

1:介紹

Spring MVC是基于組件技術的,全部的應用對象,無論是控制器和視圖,還是業務對象之類的都是java組件,并且spring mvc 不依賴于Servlet API,可以任意使用任何視圖技術,支持各種請求資源的映射策略,并且spring mvc是易于擴展的。

2:運行原理

Spring mvc的運行原理是從一個HTTP請求開始:Tomcat在啟動時加載解析web.xml,找到spring mvc的前端總控制器DispatcherServlet,并且通過DispatcherServlet來加載相關的配置文件信息。DispatcherServlet接收到客戶端請求,找到對應HandlerMapping,根據映射規則,找到對應的處理器(Handler)。調用相應處理器中的處理方法,處理該請求后,會返回一個ModelAndView。DispatcherServlet根據得到的ModelAndView中的視圖對象,找到一個合適的ViewResolver(視圖解析器),根據視圖解析器的配置,DispatcherServlet將要顯示的數據傳給對應的視圖,最后顯示給用戶。

3:常用注解

我在使用spring mvc的時候用到了很多注解,比如@RequestMapping在類面前定義,將url和類綁定。在方法面前定義 ,則將url和類的方法進行綁定。還有@RequestParam一般用于將指定的請求參數付給方法中的形參。

@Responsebody是將對象轉換為json格式進行傳輸。

@Autowired和@Resource注解的作用都是為了進行屬性注入,@Autowired默認是按照類型進行匹配的是spring提供的注解,@Resource默認是按照名字進行匹配,它是 java提供的注解 ,我一直在項目中使用的是@Autowired注入。

4:注意

spring和MVC是父子容器關系,spring是父容器,MVC是子容器.子能訪問父中的對象,而父卻不能訪問子容器中的對象.基于這點我們還可以深入一下,不用spring容器,只用mvc容器是可以的,因為它里面可以同時掃描controller層.service層.dao層的注解.而不用mvc容器,只用spring容器是不可以的,下面我們來查看具體原因,翻看源碼,從SpringMVC的DispatcherServlet開始往下找,我們發現SpringMVC初始化時,會尋找SpringMVC容器中的所有使用了@Controller注解的Bean,來確定其是否是一個handler。springMVC容器中并沒有注冊帶有@Controller注解的Bean,而是把所有帶有@Controller注解的Bean都注冊在Spring這個父容器中了,所以springMVC找不到處理器,不能進行跳轉。springmvc中處理器映射器的底層原理,是一個map(“url路徑”,controller的方法)。通過攔截請求得到相應的url路徑,然后從map中找對象的controller方法。

5:在springmvc 和 spring 都有注解掃描的前提下,不能將事務配置在Controller層?

因為事務管理器是配置在spring容器中的,如果將事務配置在Controller層的話,spring容器就訪問不了springmvc子容器,進而無法訪問到事務對象。進而導致事務失效.

(3)Mybatis

1:介紹

MyBatis是一個支持普通SQL查詢,存儲過程和高級映射的優秀持久層框架。MyBatis消除了幾乎所有的JDBC代碼和參數的手工設置以及對結果集的檢索封裝。MyBatis可以使用簡單的XML或注解用于配置和原始映射,將接口和Java的POJO(Plain Old Java Objects,普通的Java對象)映射成數據庫中的記錄。

2:Mybatis的緩存分為一級緩存和二級緩存。

一級緩存是sqlSession級別的緩存,是基于HashMap的本地緩存,不同的sqlsession之間的緩存數據區域互不影響,一級緩存的作用于是sqlsession范圍,當同一個sqlsession執行兩次相同的SQL語句時,第一次執行完后會將數據庫中插敘到的數據寫到緩存,第二次查詢從緩存中獲取,不用去查詢數據庫。當sqlsession執行insert,update,delete操作并提交到數據庫時,會先清空緩存,保證緩存中的數據是最新數據。mybatis默認開啟的是一級緩存。

二級緩存是mapper級別的緩存,同樣是基于HashMap進行存儲,多個sqlsession可以共用二級緩存,其作用域是mapper的同一個namespace。不同色sqlsession兩次執行相同的namespace下的相同的SQL語句時,會執行相同的SQL,第二次查詢只會查詢第一次查詢時讀取數據庫后寫到緩存的數據,不會再去數據庫查詢。

3:jdbc,mybatis,hibernate的區別

Hibernate屬于全自動, mybatis屬于半自動,Jdbc屬于手動,從開發效率上講hibernate較高, mybatis居中,jdbc較低,從執行效率上講hibernate較低,mybatis居中,jdbc較高,因為jdbc是手工寫sql語句,程序員對sql的控制能力更大,可以根據業務需要進行優化,而mybatis雖然也可以對sql進行優化,但是他里面將resultset封裝為實體的過程中采用了反射機制所以一定程度上影響了性能,但是Mybatis可以支持mapping映射,直接寫一個mapper接口,交給spring來管理,只要接口的方法名和sql的id保持一致,就可以輕松的調用方法。而hibernate因為高度封裝所以開發效率相對較高,但正因為這個原因,所以程序員在對sql語句的控制和優化方面相對比較弱,而且在將resultset封裝成實體的過程中也采用了反射機制,所以在性能方面比起MyBatis較低。

3:JDBC

JDBC:是java data base connectivity縮寫。用java連接數據庫

Jdbc作用:

(1)建立與數據庫的連接

(2)發送sql語句到數據庫

(3)處理返回的結果集

如何使用JDBC?

(1)準備ojdbc版本號.jar(比如ojdbc14.jar)

(2)jar包是什么?jar包就是封裝好相應功能代碼的類,通過jar包的導入,可以讓程序直接

(3)使用jar包中的方法、屬性等

使用jdbc操作數據庫:

(1)導jar包

(2)加載驅動,為數據庫連接做準備Class.forName(“oracle.jdbc.driver.OracleDriver”)

(3)準備用戶名,口令,等連接數據庫

DriverManager.getConnection(“jdbc:oracle:thin:@localhost:1521:xe”, “xxx”, “xxx”)

(4)寫sql語句

(5)創建數據庫操作對象

(6)執行sql語句

(7)關閉連接,釋放資源

Class.forName的作用?為什么要用?

按參數中指定的字符串形式的類名去搜索并加載相應的類,如果該類字節碼已經被加載過,則返回代表該字節碼的Class實例對象,否則,按類加載器的委托機制去搜索和加載該類,如果所有的類加載器都無法加載到該類,則拋出ClassNotFoundException。加載完這個Class字節碼后,接著就可以使用Class字節碼的newInstance方法去創建該類的實例對象了。

有時候,我們程序中所有使用的具體類名在設計時(即開發時)無法確定,只有程序運行時才能確定,這時候就需要使用Class.forName去動態加載該類,這個類名通常是在配置文件中配置的,例如,spring的ioc中每次依賴注入的具體類就是這樣配置的,jdbc的驅動類名通常也是通過配置文件來配置的,以便在產品交付使用后不用修改源程序就可以更換驅動類名。

4:微服務框架

4.1:什么是微服務?

簡而言之,微服務架構風格這種開發方法,是以開發一組小型服務的方式來開發一個獨立的應用系統的。其中每個小型服務都運行在自己的進程中,并經常采用HTTP資源API這樣輕量的機制來相互通信。這些服務圍繞業務功能進行構建,并能通過全自動的部署機制來進行獨立部署。這些微服務可以使用不同的語言來編寫,并且可以使用不同的數據存儲技術。對這些微服務我們僅做最低限度的集中管理。

4.2:微服務具備的特性?

  1. 每個微服務可獨立運行在自己的進程里;
  2. 一系列獨立運行的微服務共同構建起了整個系統;
  3. 每個服務為獨立的業務開發,一個微服務一般完成某個特定的功能,比如:訂單管理、用戶管理等;
  4. 微服務之間通過一些輕量的通信機制進行通信,例如通過REST API或者RPC的方式進行調用。
  5. 4.3:微服務優點
  6. 易于開發和維護,啟動較快,局部修改容易部署,技術棧不受限,按需伸縮,DevOps
  7. 4.4:微服務帶來的挑戰
  8. 運維要求較高,分布式的復雜性,接口調整成本高,重復勞動
  9. 4.5:微服務設計原則
  10. 單一職責原則,服務自治原則,輕量級通信原則,接口明確原則

1:SpringBoot

Springboot框架在使用過程中也是比較簡單的,我們當時整合mybatis后,直接啟動就可以使用了。整合mybatis也是比較簡單的,首先在pom.xml中,配置加載spring-boot-starter-parent父類jar包,再引入spring-boot-starter配置。如果是搭建了web項目的話,還需要引入spring-boot-data-web jar包,當時我們是整合mybatis持久層框架,所以需要導入mybatis-spring-boot-starter和mysql-connecter-java整合包,這樣就配置完成了。

另外項目中鏈接數據源有兩種方式,通過application.properties文件,或者application.yml文件,配置文件中必須安裝數據庫鏈接設置。因為springboot沒有配置文件,所有的加載都是通過注解來生效的,使用的注解也比較多。

項目啟動的時候,使用@SpringbootApplication放到啟動類上,直接執行main方法就可以了,需要注意的是啟動類必須放到根包下,這樣才能掃描到所有的類。我們還需要在控制層類上加上@RestController注解(他相當于是spring-mvc中的@ResponseBody和@Controller的結合),其他的注解和spring,spring-mvc的注解差不多了,比如@Controller,@RequestMapping,@Service,@PathVilable,@Value等。用generator生成基本的增刪改查,復雜業務邏輯寫sql語句。

除了使用mybatis外,當時我們還查到了springboot和jpa的整合,因為jpa是不寫入sql的所以當時就沒有使用,其實jpa使用起來挺簡單的,它是通過方法名來進行對數據庫的操作,方法名的命名也是要有一定的規則的,dao層的接口需要繼承JpaRepositort<>。

在我們的項目中,考慮到相應的節假日,網站活動的調整和頁面的渲染,所以采用了頁面靜態化的處理,我們用的是thymeleaf,其實也可以用freemarker,但是當時我上網查了一下發現springboot整合thymeleaf比較好一些,所以就是用了thymeleaf。

Thymeleaf也是一款用于渲染xml、xhtml、html5內容的模板引擎,其實跟valocity和freem

arker差不多,我在網上看了一下,thymeleaf和springboot整合還是很好用的,結構很明顯,只是在對應的標簽中加上對應的屬性就行了。如th:text設置文本內容,th:href設置路徑,th:each循環數據等。

另外springboot還可以整合前段框架,有一個webjars官網可以直接找到前段配置的jar包,直接引入到pom.xml中,讓前段框架也交給maven處理。

考慮到項目中要使用redis緩存服務器,我們當時就整合了redis的主從配置5臺redis緩存服務器,還有哨兵機制。整合redis也比較簡單,也是在pom.xml中配置引入spring-boot-starter-data-redis,當時我上網查了一下發現,redis的1.4.7版本以上的需要引入spring-boot-starter-data-redis,而1.4.7版本以下的需要引入spring-boot-starter-redis。在application.properties文件中引入redis的相關配置,有端口號,ip地址,鏈接的數據庫等,直接配置就可以,只要redis服務器啟動,項目就可以使用了。當時配置的時候,在啟動類上加 @EnableCaching注解,開啟緩存,這樣就可以在業務層實現類的方法上面加上@Cacheable注解就可以使用了,這時候加載到方法后,首先去redis當中取對應數據,如果有數據,從緩存當中獲取,如果沒有對應數據,再從數據庫中獲取數據。

當時項目中也涉及到了多數據源的動態切換,在以前的項目中我們是使用spring的aop前置通知類實現數據源的動態切換,使用aop前置通知判斷到底是什么操作,如果是增刪改的操作,切換到主數據庫,如果是查詢操作,切換到從數據庫?,F在使用springboot,實現動態切換數據源就比較簡單了。首先在application.properties文件中,配置多個數據源鏈接信息,使用的時候持久層接口通過包結構來區分到底走哪一個數據庫。寫一個配置類,在類上面加上,@Configuration、@MapperScan(basePackages=“”,sqlSessionTemplateRef=)

來設置配置,有幾個數據源,配置幾個配置類,然后在項目中通過業務邏輯類判斷到底走哪一個數據源。

另外,在項目中還配置了RabbitMQ消息隊列服務器,rabbitMQ是一個異步通信,與activeMQ相比,只是多了一個交換機的概念,它主要包括,生產者、交換機、隊列、消費者。它的配置也比較簡單,在pom.xml文件中加載對應的jar包spring-boot-starter-amqp,amqp是高級消息隊列協議,消息生產者調用AmqpTemplate rabbitTemplate,直接使用rabbitTempla.convertAndSend(message),發送到rabbitMQ中,通過交換機放到指定的隊列當中,消費者通過@RabbitListener(queues=””)來監聽對應的隊列獲得信息,通過@RabbitHandler注解來處理監聽到的信息。

消息隊列,容易丟失隊列數據如何處理?:

解決方案:1.使用mongodb進行數據的備份,電商業務下訂單時, 會將所有的訂單先發送到消息隊列中,供后續監聽獲得數據操作,為了防止訂單數據丟失問題,使用mongodb數據庫下訂單時,發送到rabbitmq的同時,會將訂單信息存入mongodb中備份,同時添加一個標識字段0:未對賬,1:已對賬。

2.另外設置一個springboot定時器,每月月底定時查閱mongodb數據庫中一個月以前的數據信息,如果發現mongodb數據信息中有標識還為0:未對賬的信息,會將該條信息重新加入到消息隊列中進行處理)。剛才說道定時器了,我們也沒有使用Quartz定時器,我們使用的是springboot整合的定時器,直接在springboot啟動類上添加@EnableScheduling就可以,然后再具體執行的類上加上@Scheduled(cron="*/6 * * * * ?"), 通過表達式來定義。另外還有發郵件功能,pom.xml配置文件中添加spring-boot-starter-mail.

Springboot整合mongodb也比較簡單,在pom.xml中加載配置spring-boot-starter-data-mongodb,然后在application.properties文件中配置mongodb數據庫鏈接信息,spring.data.mongodb.uri=mongodb://name:pass@localhost:27017/test,如果有多個IP集群:spring.data.mongodb.uri=mongodb://user:pwd@ip1:port1,ip2:port2/database創建實體dao,在持久層注入MongoTemplate模板,使用模板來實現對數據庫的ICUD操作。

如果是多個數據源,在pom.xml文件中加入lombok和spring-boot-autoconfigure包引用。

Lombok - 是一個可以通過簡單的注解形式來幫助我們簡化消除一些必須有但顯得很臃腫的Java代碼的工具,通過使用對應的注解,可以在編譯源碼的時候生成對應的方法。加上注解我們就不用手動寫 getter\setter、構建方式類似的代碼了。

spring-boot-autoconfigure - 就是spring boot的自動化配置.

在application.properties文件中加入額外的數據源信息.配置不同包路徑下使用不同的數據源,通過@Configuration申明配置類@EnableMongoRepositories注解指出包的路徑,創建兩個庫分別對應的對象和Repository借助lombok來構建對象,到此,mongodb多數據源的使用已經完成。

2:SpringCloud

Spring Cloud是一系列框架的有序集合。它利用Spring Boot的開發便利性巧妙地簡化了分布式系統基礎設施的開發,如服務發現注冊、配置中心、消息總線、負載均衡、斷路器、數據監控等,都可以用Spring Boot的開發風格做到一鍵啟動和部署。Spring并沒有重復制造輪子,它只是將目前各家公司開發的比較成熟、經得起實際考驗的服務框架組合起來,通過Spring Boot風格進行再封裝屏蔽掉了復雜的配置和實現原理,最終給開發者留出了一套簡單易懂、易部署和易維護的分布式系統開發工具包。

微服務是可以獨立部署、水平擴展、獨立訪問(或者有獨立的數據庫)的服務單元,Spring Cloud就是這些微服務的大管家,采用了微服務這種架構之后,項目的數量會非常多,Spring Cloud做為大管家就需要提供各種方案來維護整個生態。

Spring Cloud就是一套分布式服務治理的框架,既然它是一套服務治理的框架,那么它本身不會提供具體功能性的操作,更專注于服務之間的通訊、熔斷、監控等。

相關知識

免费 无码 国产在线观看观-亚洲精品乱码久久久久-久久精品无码一区二区国产-国产欧美一区二区精品久久久