Le mécanisme de mise en cache de Spring est très flexible et peut mettre en cache toutes les méthodes de haricots ou de haricots dans le récipient. Par conséquent, ce mécanisme de mise en cache peut être mis en cache à n'importe quel niveau d'application Javaee.
La couche sous-jacente de cache de ressort doit également être implémentée à l'aide d'autres outils de cache, tels que ehcache (Hibernate Cache Tool), et la couche supérieure utilise une programmation API unifiée.
Pour utiliser le cache de ressort, les trois étapes suivantes sont nécessaires
Par exemple
<? xml version = "1.0" encoding = "utf-8"?> <ehcache> <diskstore path = "java.io.tmpdir" /> <! - Configurez le cache par défaut -> <defaultCache maxElementsInMemory = "10000" eteral = "False" TimeToileSonds = "120" timetoliveSeconds = "120" timeTeconds = "120" timetoliveds = "120" timeTeconds = "120" timetoliveds) " maxelementsondisk = "10000000" diskexpirythreadintervalsEconds = "120" memorystoreevictionpolicy = "lru" /> <! - Configurez le cache nommé utilisateurs -> <cache name = "utilisateurs" maxelementsinmemory = "10000" eternal = "false" qui sure TIMETOLIVESECONDS = "600" /> </ ehcache>
Le ehcache.xml ci-dessus configure deux zones de cache. Les haricots au printemps seront mis en cache dans ces zones de cache. Généralement, le nombre de haricots dans le conteneur à ressort sera défini à Ehcache.
Configurez ensuite le gestionnaire de cache dans le fichier de configuration Spring comme suit, où le premier bean est un bean d'usine utilisé pour configurer le cacheManager d'Ehcache, et le deuxième bean est le gestionnaire de cache configuré pour le cache de ressort, de sorte que le premier bean est injecté dans le deuxième haricot.
<cache: cache-manager basé sur l'annotation = "cacheManager" /> <! - Configurez ehcache cacheManager pour spécifier l'emplacement du fichier ehcache.xml via la configlocation -> <bean id = "ehcachemanager" p: configLocation = "classpath: ehcache.xml" p: shared = "false" /> <! Injecter ehcache cachemanager dans le gestionnaire de cache Bean -> <bean id = "cacheManager" p: cacheManager-ref = "ehcacheManager"> </Eb>
Voici une configuration de ressort complète.
<? xml version = "1.0" encoding = "utf-8"?> <beans xmlns = "http://www.springframework.org/schema/beans" xmlns: xsi = "http://www.w3.org/2001/xmlschema-instance" xmlns: p = "http://www.springframework.org/schema/p" xmlns: cache = "http://www.springframework.org/schema/cache" xmlns: context = "http://www.springframeworkwork.org/schema/contex" xsi: schemalocation = "http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/springframeworks http://www.springframework.org/schema/cache/spring-cache-4.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.0. Base-Package = "com.service" /> <cache: annotation-axé cache-manager = "cacheManager" /> <! - Configurer ehcache cacheManager spécifiez l'emplacement du fichier ehcache.xml via la configlocation -> <bean id = "ehcachemanager" p: configlocation = "Classpath: <! - Configurez le gestionnaire de cache basé sur EHCACH et injectez CacheManager d'Ehcache dans le gestionnaire de cache Bean -> <Bean Id = "Cachemanager" P: CacheManager-Ref = "EhcacheManager"> </Eb> </EANS>
Les éléments suivants utiliseront @Cacheable comme exemple pour démontrer l'utilisation du ressort basé sur le cache ehcache. Cacheable est utilisé pour modifier des classes ou des méthodes. Si la classe est modifiée, toutes les méthodes de la classe seront mises en cache.
Cache au niveau de la classe
Par exemple, il y a les classes de haricots suivantes,
@Service ("userService") @ cacheable (value = "utilisateurs") classe publique UserServiceIMPl implémente userService {@Override public user GetUserSbyNameAndage (nom de chaîne, int age) {System.out.println ("Executing GetUsersByNameAnDage () .."); retourner un nouvel utilisateur (nom, âge); } @Override public utilisateur Getanotheuser (nom de chaîne, int age) {System.out.println ("exécutant getanotheuser () .."); retourner un nouvel utilisateur (nom, âge); }}Le cache basé sur la classe mettra en cache toutes les méthodes de la classe. Après Cache, le programme appelle toute méthode de l'instance de cette classe. Tant que les paramètres passés sont les mêmes, Spring n'exécutera pas réellement la méthode, mais recherchera directement les données en cache en fonction des paramètres passés!
Par exemple, utilisez des données mises en cache comme ci-dessous.
public static void test2 () {applicationContext ctx = new ClassPathxMlApplicationContext ("beans.xml"); UserService US = ctx.getBean ("userService", userService.class); User u1 = us.getUserSByNameAnDage ("Zhang San", 50); // Parce que le même paramètre est utilisé lorsque la méthode de service d'utilisateur est appelée deuxième fois, la méthode réelle ne sera pas exécutée, // Spring recherchera directement les données par paramètres de l'utilisateur de cache U2 = us.getanotherUser ("Zhang SAN", 50); System.out.println (U1 == U2); }Résultat de sortie,
GetUsersByNameAndage () est en cours d'exécution.
vrai
Comme vous pouvez le voir, le getanotheuser () ci-dessus n'est pas réellement exécuté car les paramètres passés sont les mêmes que les paramètres transmis par la méthode précédente, donc le ressort provient directement des données de zone de cache.
En plus de la valeur d'attribut requise, l'annotation @Cacheable dans la classe Bean ci-dessus a également des attributs de clé, de condition et à moins que Les trois derniers sont utilisés pour définir des politiques de stockage de ressort. Pour les caches basées sur les classes, Spring utilise les paramètres passés dans la méthode comme clé pour rechercher les résultats dans le cache par défaut.
Bien sûr, nous pouvons également modifier la stratégie de la clé et laisser le printemps suivre d'autres normes, telles que la question de savoir si le premier paramètre est le même que la clé, et rechercher les résultats dans le cache.
Modifiez la classe de bean ci-dessus comme suit,
@Service ("userService") @ cacheable (value = "utilisateurs", key = "# name") classe publique UserServiceIMPl implémente userService {@Override public utilisateur getUSERSBYNAMEAnDAGE (String Name, int Age) {Ce qui signifie que nous passons le même nom, Spring n'exécutera pas vraiment la méthode. Ce n'est que lorsque le nom est différent, la méthode sera exécutée, par exemple,
public static void test2 () {applicationContext ctx = new ClassPathxMlApplicationContext ("beans.xml"); UserService US = ctx.getBean ("userService", userService.class); User u1 = us.getUserSByNameAnDage ("Zhang San", 50); // Après avoir modifié le paramètre de clé de @cacheable en key = "# name", la méthode suivante pourra être exécutée. User u2 = us.getanotheUser ("Li si", 50); System.out.println (U1 == U2); } Vous pouvez voir que cette fois getAnotherUser() a été exécutée.
1 getUsersByNameAndage () est en cours d'exécution.
2 Getanotheuser () est en cours d'exécution.
3 faux
Nous pouvons également définir la propriété de condition, par exemple,
@Service ("userService") @ cacheable (value = "utilisateurs", condition = "# age <100") classe publique UserServiceIMPl implémente UserService {@Override public utilisateur getUSERSBYNAMEAnDAGE (Nom de la chaîne, Int Age) {Ainsi, pour le code suivant, aucune méthode ne sera mise en cache. Spring exécute la méthode réelle pour obtenir le résultat à chaque fois.
public static void test2 () {applicationContext ctx = new ClassPathxMlApplicationContext ("beans.xml"); UserService US = ctx.getBean ("userService", userService.class); Utilisateur U1 = us.getUserSByNameAndage ("Zhang San", 500); User u2 = us.getanotherUser ("Li si", 500); System.out.println (U1 == U2); }Résultats de l'exécution,
GetUsersByNameAndage () est en cours d'exécution.
Getanotheuser () est en cours d'exécution.
FAUX
Le cache au niveau de la méthode ne fonctionnera que pour la méthode. Différentes méthodes peuvent définir des zones de cache inutiles, comme les suivantes,
@Service ("userService") classe publique UserServiceImpl implémente userService {@cacheable ("users1") @Override public utilisateur getUSERSBYNAMEAnDAGE (String Name, int Age) {System.out.println ("Execution GetUsersByNameAndage () .."); retourner un nouvel utilisateur (nom, âge); } @Cacheable ("Users2") @Override public utilisateur GetanotheUser (nom de chaîne, int age) {System.out.println ("getanotheuser () .."); retourner un nouvel utilisateur (nom, âge); }}Utilisez le code de test suivant,
public static void test2 () {applicationContext ctx = new ClassPathxMlApplicationContext ("beans.xml"); UserService US = ctx.getBean ("userService", userService.class); // La première fois que la méthode est exécutée, la méthode sera exécutée et mise en cache u1 = us.getUserSByNameAndage ("Zhang San", 500); // Bien que la méthode suivante passe les mêmes paramètres, car ces deux méthodes sont dans différentes zones de cache, les données de cache ne peuvent pas être utilisées. User U2 = us.getanotheUser ("Zhang San", 500); System.out.println (U1 == U2); // Ce qui précède a été mis en cache, et il ne sera pas exécuté ici. Utilisez le cache directement. User u3 = us.getanotheuser ("Zhang San", 500); System.out.println (U3 == U2); }Résultats de l'exécution,
GetUsersByNameAndage () est en cours d'exécution.
Getanotheuser () est en cours d'exécution.
FAUX
vrai
La méthode modifiée par @cacheevict peut être utilisée pour effacer le cache, et les propriétés suivantes peuvent être spécifiées à l'aide @CacheEvict .
Allentries, s'il faut effacer toute la zone de cache
AVANTInvocation: s'il faut effacer le cache avant d'exécuter la méthode. La valeur par défaut est de ne l'effacer qu'après que la méthode est exécutée avec succès.
condition et clé, la même signification que dans @Cacheable .
La démonstration suivante est simple.
@Service ("userService") @ cacheable ("utilisateurs") classe publique UserServiceIMPl implémente userService {@Override public utilisateur getUSERSBYNAMEAnDAGE (nom de chaîne, int) {System.out.println ("Exécution getUSERSBYNAMEAnDAG {System.out.println ("Exécution de getanotheuser () .."); retourner nouvel utilisateur (nom, âge);} // spécifiez le cache clair selon le nom et les paramètres de l'âge @cacheevict (value = "utilisateurs") public Void Evictuner (String Name, int Age) {System.out.println ("- Effacer le cache correspondant de" + name + ",");); Effacement de toutes les données mises en cache dans la zone de cache utilisateur @cacheevict (value = "utilisateurs", allentries = true) public void evictall () {System.out.println ("- effacer l'intégralité du cache--");}}Vous trouverez ci-dessous la classe de test,
public static void test2 () {applicationContext ctx = new ClassPathxMlApplicationContext ("beans.xml"); UserService US = ctx.getBean ("userService", userService.class); // Le système mettra en cache deux méthodes utilisateur u1 = us.getUserSByNameAndage ("Zhang San", 500); User u2 = us.getanotheUser ("Li si", 400); // appelle la méthode Evictuser () pour effacer les données spécifiées dans le tampon us.evictuser ("li si", 400); // Clear li si, 400 avant que les données renvoyées par la méthode suivante ne soient en cache à nouveau l'utilisateur u3 = us.getanotheuser ("li si", 400); System.out.println (US == U3); // FAUX // Les données de Zhang SAN et 500 ont déjà été mises en cache, et la méthode suivante ne sera pas réexécutée, et les données du cache seront directement récupérées U4 = US.GetanotherUser ("Zhang San", 500); System.out.println (U1 == U4); // output true // effacer l'intégralité du cache us.evictall (); // Parce que l'ensemble du cache a été effacé, le code suivant sera réexécuté l'utilisateur u5 = us.getanotheuser ("Zhang San", 500); User u6 = us.getanotherUser ("li si", 400); System.out.println (U1 == U5); // Sortie False System.out.println (U3 == U6); // Sortie fausse}Résultats de l'exécution,
GetUsersByNameAndage () est en cours d'exécution.
Getanotheuser () est en cours d'exécution.
- Répartir le cache correspondant à Li si, 400-
Getanotheuser () est en cours d'exécution.
FAUX
vrai
- Répartir l'intégralité du cache-
Getanotheuser () est en cours d'exécution.
Getanotheuser () est en cours d'exécution.
FAUX
FAUX
Ce qui précède est tout au sujet de l'exemple de mécanisme de mise en cache de printemps dans cet article, j'espère que cela sera utile à tout le monde. Les amis intéressés peuvent continuer à se référer à d'autres sujets connexes sur ce site. S'il y a des lacunes, veuillez laisser un message pour le signaler. Merci vos amis pour votre soutien pour ce site!