1 @CacheEvict
@CacheEvict是Spring框架中用于清空緩存的注解。以下是對@CacheEvict注解的詳細介紹:
1.1 作用
@CacheEvict注解的主要作用是刪除緩存中的數據。在方法執行后或執行前(根據配置),它可以清空指定的緩存項或整個緩存區域。這對于刪除舊的數據或無效的數據非常有用,可以確保緩存中的數據始終是最新的。
1.2 常用屬性
@CacheEvict注解包含多個屬性,用于配置緩存刪除的行為:
- value/cacheNames:指定要清空的緩存的名稱。可以是一個字符串或一個字符串數組,表示該方法將清空哪個緩存區域中的數據。如果指定了多個緩存名稱,那么這些緩存區域中的數據都將被清空。
- key:指定要清空的緩存項的鍵。通過該屬性,可以精確控制要刪除的緩存數據。可以使用SpEL表達式來動態生成鍵的值。
- allEntries:一個布爾值,用于指定是否清空緩存中的所有數據。如果設置為true,那么將刪除指定緩存區域中的所有數據;如果設置為false(默認值),則只刪除與指定鍵相匹配的緩存項。
- beforeInvocation:一個布爾值,用于指定是否在方法執行前清空緩存。如果設置為true,那么緩存的清空操作將在方法執行之前進行;如果設置為false(默認值),則緩存的清空操作將在方法執行之后進行。需要注意的是,如果在方法執行前清空緩存,并且方法執行失敗(拋出異常),那么緩存將不會被重新填充。
1.3 使用示例
以下是一個使用@CacheEvict注解的示例:
@Service
public class UserService {@Autowiredprivate UserRepository userRepository;// 使用@Cacheable注解緩存用戶數據@Cacheable(value = "users", key = "#id")public User getUserById(Long id) {return userRepository.findById(id).orElse(null);}// 使用@CacheEvict注解刪除用戶數據對應的緩存@CacheEvict(value = "users", key = "#user.id")public void saveUser(User user) {userRepository.save(user);}
}
在上面的示例中,UserService類中的getUserById方法使用了@Cacheable注解來緩存用戶數據。而saveUser方法則使用了@CacheEvict注解來刪除與保存的用戶數據相對應的緩存項。這樣,在每次保存用戶數據后,都可以確保緩存中的數據是最新的。
1.4 注意事項
- 在使用@CacheEvict注解時,必須指定要清空的緩存名稱(value/cacheNames屬性)和緩存項的鍵(key屬性)。
- 如果指定了allEntries屬性為true,那么將刪除指定緩存區域中的所有數據,因此需要謹慎使用。
- 如果在方法執行前清空緩存(beforeInvocation屬性為true),并且方法執行失敗,那么緩存將不會被重新填充。這可能會導致在某些情況下出現數據不一致的問題。因此,在使用beforeInvocation屬性時,需要充分考慮方法的執行情況和可能的異常處理。
總之,@CacheEvict注解是Spring框架中用于清空緩存的重要工具。通過合理配置其屬性,可以實現對緩存數據的精確控制和管理。
2 @Caching
@Caching注解是Spring Cache提供的一個功能強大的組合注解,它允許開發者在一個方法或類上同時指定多個緩存操作相關的注解。以下是關于@Caching注解的詳細介紹:
2.1 @Caching注解的主要功能
@Caching注解通過組合多個Spring Cache注解(如@Cacheable、@CachePut、@CacheEvict等),能夠定義復雜的緩存規則。這使得開發者可以在一個方法上靈活地配置多種緩存行為,而無需編寫重復的緩存處理代碼。
2.2 @Caching注解的屬性
@Caching注解擁有三個主要屬性,每個屬性都可以接收一個或多個相應的注解作為值:
- cacheable:用于指定一個或多個@Cacheable注解的組合。@Cacheable注解用于查詢緩存,如果緩存中存在相應的數據,則直接返回緩存數據而不執行方法。如果沒有緩存數據,則執行方法并將結果添加到緩存中。
- put:用于指定一個或多個@CachePut注解的組合。@CachePut注解無論方法是否被執行,都會將方法的返回值放入指定的緩存中。這通常用于更新緩存數據。
- evict:用于指定一個或多個@CacheEvict注解的組合。@CacheEvict注解用于刪除緩存中的數據,通常用于刪除操作或數據更新后的緩存同步。
2.3 @Caching注解的使用示例
以下是一個使用@Caching注解的示例,展示了如何在一個方法上同時指定查詢緩存、更新緩存和刪除緩存的操作:
@Caching(cacheable = @Cacheable(key = "'userCache:'+ #uid"),put = @CachePut(key = "'userCache:'+ #uid"),evict = { @CacheEvict(key = "'userCache:'+ #uid"), @CacheEvict(key = "'addressCache:'+ #uid"), @CacheEvict(key = "'messageCache:'+ #uid") }
)
public User updateRef(String uid) {// 業務邏輯return null;
}
在這個示例中,updateRef
方法被配置了多個緩存操作:
- 使用@Cacheable注解查詢
userCache
緩存,如果緩存中存在以uid
為鍵的數據,則直接返回該數據。 - 使用@CachePut注解更新
userCache
緩存,將方法的返回值放入緩存中。 - 使用多個@CacheEvict注解刪除
userCache
、addressCache
和messageCache
緩存中以uid
為鍵的數據。
2.4 @Caching注解的注意事項
- SpEL表達式:在@Caching注解的屬性中,可以使用Spring Expression Language(SpEL)表達式來動態生成緩存的鍵(key)。這提供了很大的靈活性,允許開發者根據方法的參數或返回值來定制緩存的鍵。
- 緩存配置:在使用@Caching注解之前,需要確保已經配置了Spring Cache的相關依賴和緩存管理器(CacheManager)。這通常通過在Spring Boot應用程序的主類或配置類上使用@EnableCaching注解來啟用緩存支持,并通過application.properties或application.yml文件進行自定義配置。
- 緩存同步:在使用@Cacheable和@CachePut注解時,需要注意緩存的同步問題。如果多個線程同時訪問同一個緩存鍵,可能會導致數據不一致的問題。因此,在使用這些注解時,需要確保緩存的同步機制得到妥善處理。
綜上所述,@Caching注解是Spring Cache提供的一個非常有用的工具,它允許開發者在一個方法或類上同時指定多個緩存操作相關的注解。通過合理使用@Caching注解,可以大大提高應用程序的性能和可維護性。
3 @After 、@Before 、@ Around
@After
、@Before
和 @Around
是Spring AOP(面向切面編程)中的注解,它們用于定義切面的通知(Advice),這些通知在目標方法執行的不同階段執行額外的邏輯。以下是這些注解的詳細介紹及示例:
3.1 @Before
注解
- 作用:前置通知,在目標方法執行之前執行。它通常用于執行一些前置條件檢查、日志記錄等。
- 示例:
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;@Aspect
@Component
public class MyBeforeAdvice {@Before("execution(* com.example.service.*.*(..))")public void beforeAdvice() {System.out.println("Before method execution");// 在這里可以執行前置邏輯,如日志記錄、權限檢查等}
}
在這個例子中,beforeAdvice
方法會在 com.example.service
包下所有類的所有方法執行之前執行。
3.2 @After
注解
- 作用:后置通知,在目標方法執行之后執行,無論目標方法是否拋出異常。它通常用于執行一些清理工作、日志記錄等。
- 示例:
import org.aspectj.lang.annotation.After;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;@Aspect
@Component
public class MyAfterAdvice {@After("execution(* com.example.service.*.*(..))")public void afterAdvice(JoinPoint joinPoint) {System.out.println("After method execution: " + joinPoint.getSignature());// 在這里可以執行后置邏輯,如日志記錄、資源釋放等}
}
在這個例子中,afterAdvice
方法會在 com.example.service
包下所有類的所有方法執行之后執行。
3.3 @Around
注解
- 作用:環繞通知,可以包裹目標方法的執行,擁有最大的控制權。它可以在目標方法執行前后執行自定義邏輯,甚至可以決定是否繼續執行目標方法或改變其返回值。
- 示例:
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;@Aspect
@Component
public class MyAroundAdvice {@Around("execution(* com.example.service.*.*(..))")public Object aroundAdvice(ProceedingJoinPoint pjp) throws Throwable {System.out.println("Before method execution");try {Object result = pjp.proceed(); // 執行目標方法System.out.println("After method execution");return result; // 返回目標方法的執行結果} catch (Throwable throwable) {// 處理異常System.out.println("Exception occurred: " + throwable.getMessage());throw throwable; // 重新拋出異常}}
}
在這個例子中,aroundAdvice
方法會在 com.example.service
包下所有類的所有方法執行前后執行自定義邏輯。它首先打印“Before method execution”,然后執行目標方法,并打印“After method execution”。如果目標方法拋出異常,它還會捕獲并處理該異常。
3.4 總結
@Before
注解用于在目標方法執行之前執行前置邏輯。@After
注解用于在目標方法執行之后執行后置邏輯,無論目標方法是否拋出異常。@Around
注解用于在目標方法執行前后執行自定義邏輯,并可以控制是否繼續執行目標方法或改變其返回值。
這些注解在Spring AOP中非常有用,可以幫助開發者在不修改目標方法代碼的情況下實現各種復雜的功能和邏輯。
4 docker network
Docker提供了一組命令來管理和配置Linux網絡,這些命令可以創建、列出、刪除和檢查網絡,幫助用戶在Docker容器之間建立通信。以下是一些常用的Docker網絡命令及其詳細介紹:
4.1 創建網絡
-
命令:
docker network create [OPTIONS] NETWORK_NAME
-
功能:創建一個新的Docker網絡。
-
選項:
--driver
:指定網絡驅動程序(如bridge、host、overlay等)。--subnet
:指定子網。--gateway
:指定網關。--ip-range
:指定可用IP地址范圍。--ipv6
:啟用IPv6。--label
:為網絡添加標簽。
-
示例:
docker network create --driver bridge --subnet 192.168.1.0/24 my_network
4.2 列出網絡
- 命令:
docker network ls
- 功能:列出所有可用的Docker網絡。
- 輸出:包括NETWORK ID、NAME、DRIVER和SCOPE等信息。
4.3 查看網絡詳情
- 命令:
docker network inspect [OPTIONS] NETWORK_NAME
- 功能:查看指定Docker網絡的詳細信息。
- 輸出:包括網絡名稱、ID、創建時間、作用域、驅動程序、IPAM配置(子網、網關等)、容器連接信息等。
4.4 連接容器到網絡
-
命令:
docker network connect [OPTIONS] NETWORK_NAME CONTAINER_NAME
-
功能:將已創建的容器連接到指定的Docker網絡中。
-
選項:無特定選項,但可以使用
--alias
為容器在網絡中設置別名。 -
示例:
docker network connect my_network my_container
4.5 斷開容器與網絡的連接
-
命令:
docker network disconnect [OPTIONS] NETWORK_NAME CONTAINER_NAME
-
功能:斷開指定容器與指定Docker網絡的連接。
-
選項:無特定選項。
-
示例:
docker network disconnect my_network my_container
4.6 刪除網絡
-
命令:
docker network rm [OPTIONS] NETWORK_NAME
-
功能:刪除指定的Docker網絡。
-
選項:無特定選項,但可以同時刪除多個網絡,如
docker network rm network1 network2
。 -
示例:
docker network rm my_network
4.7 其他注意事項
- 網絡類型:Docker支持多種網絡類型,包括bridge(橋接網絡,默認類型)、host(主機網絡)、overlay(覆蓋網絡,用于多主機集群)等。
- 網絡隔離:通過創建不同的網絡,可以實現容器之間的隔離,提高安全性。
- 容器間通信:容器可以通過自定義網絡在不同主機上安全地相互通信。
綜上所述,Docker網絡命令提供了強大的網絡管理功能,允許用戶創建、配置和管理Docker容器之間的網絡連接。通過使用這些命令,用戶可以實現容器之間的隔離、通信和網絡配置,滿足各種復雜的網絡需求。
5 ElasticsearchTemplate 和 RestHighLevelClient
ElasticsearchTemplate 和 RestHighLevelClient 都是用于與 Elasticsearch 進行交互的客戶端工具,但它們在實現方式、使用場景和功能特點上有所不同。以下是對兩者的詳細介紹以及它們之間的區別:
5.1 ElasticsearchTemplate
-
概述:
ElasticsearchTemplate 是 Spring Data Elasticsearch 提供的一個高級抽象,它封裝了底層的 Elasticsearch 客戶端操作,使得開發者可以更方便地與 Elasticsearch 進行交互。 -
特點:
- 簡化操作:通過提供一系列的方法,如索引、查詢、刪除等,簡化了與 Elasticsearch 的交互過程。
- 豐富的操作方法:支持各種 CRUD 操作,以及復雜的查詢和聚合操作。
- 自定義查詢:允許開發者通過 Java 代碼構建自定義的查詢條件,滿足更復雜的業務需求。
-
使用場景:
- 適用于使用 Spring 框架的開發者,特別是那些希望利用 Spring Data Elasticsearch 提供的便利性和豐富功能的開發者。
5.2 RestHighLevelClient
-
概述:
RestHighLevelClient 是 Elasticsearch 官方提供的一個高級 REST 客戶端,它基于 HTTP 協議與 Elasticsearch 進行交互。與低級的 REST 客戶端相比,RestHighLevelClient 提供了更高的抽象層次和更豐富的功能。 -
特點:
- 官方支持:由 Elasticsearch 官方提供,與 Elasticsearch 的兼容性更好。
- 豐富的 API:提供了包括索引管理、數據管理、查詢等在內的豐富 API。
- 高性能:通過優化 HTTP 請求和響應的處理,提高了與 Elasticsearch 交互的性能。
-
功能:
- 索引管理:支持創建、刪除、判斷索引是否存在等操作。
- 數據管理:支持寫入、批量寫入、更新等操作。
- 查詢功能:支持基本查詢、復合查詢、聚合查詢等,可以結合原生 Elasticsearch 查詢語法實現更復雜的查詢需求。
-
使用場景:
- 適用于需要在 Java 應用程序中集成 Elasticsearch 的開發者,特別是那些希望使用 Elasticsearch 官方提供的高級 REST 客戶端的開發者。
5.3 兩者區別
-
實現方式:
- ElasticsearchTemplate 是基于 Spring Data Elasticsearch 的,它封裝了底層的 Elasticsearch 客戶端操作,提供了更高層次的抽象。
- RestHighLevelClient 是 Elasticsearch 官方提供的 REST 客戶端,它基于 HTTP 協議與 Elasticsearch 進行交互,提供了更豐富的 API 和更高的性能。
-
使用場景:
- ElasticsearchTemplate 更適用于使用 Spring 框架的開發者,特別是那些希望利用 Spring Data Elasticsearch 的便利性和豐富功能的開發者。
- RestHighLevelClient 則更適用于需要在 Java 應用程序中集成 Elasticsearch 的開發者,特別是那些希望使用 Elasticsearch 官方提供的高級 REST 客戶端的開發者。
-
功能特點:
- ElasticsearchTemplate 提供了豐富的操作方法,但相對來說,它的抽象層次更高,可能對于某些復雜的查詢需求需要開發者進行更多的自定義封裝。
- RestHighLevelClient 則提供了更豐富的 API 和更高的性能,對于復雜的查詢需求,它可以更好地結合原生 Elasticsearch 查詢語法來實現。
綜上所述,ElasticsearchTemplate 和 RestHighLevelClient 都是用于與 Elasticsearch 進行交互的重要工具,但它們在實現方式、使用場景和功能特點上有所不同。開發者在選擇時,應根據自己的技術棧、業務需求以及對 Elasticsearch 的熟悉程度來做出決策。