Skip to content

Commit 95699c5

Browse files
committed
2 parents 87cc4df + c459b92 commit 95699c5

22 files changed

+944
-465
lines changed

caching/README.md

Lines changed: 66 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -43,39 +43,29 @@ Wikipedia says:
4343
**Programmatic Example**
4444

4545
Let's first look at the data layer of our application. The interesting classes are `UserAccount`
46-
which is a simple Java object containing the user account details, and `DbManager` which handles
47-
reading and writing of these objects to/from MongoDB database.
46+
which is a simple Java object containing the user account details, and `DbManager` interface which handles
47+
reading and writing of these objects to/from database.
4848

4949
```java
50-
@Setter
51-
@Getter
50+
@Data
5251
@AllArgsConstructor
5352
@ToString
53+
@EqualsAndHashCode
5454
public class UserAccount {
5555
private String userId;
5656
private String userName;
5757
private String additionalInfo;
5858
}
5959

60-
@Slf4j
61-
public final class DbManager {
62-
63-
private static MongoClient mongoClient;
64-
private static MongoDatabase db;
65-
66-
private DbManager() { /*...*/ }
67-
68-
public static void createVirtualDb() { /*...*/ }
69-
70-
public static void connect() throws ParseException { /*...*/ }
71-
72-
public static UserAccount readFromDb(String userId) { /*...*/ }
60+
public interface DbManager {
7361

74-
public static void writeToDb(UserAccount userAccount) { /*...*/ }
75-
76-
public static void updateDb(UserAccount userAccount) { /*...*/ }
77-
78-
public static void upsertDb(UserAccount userAccount) { /*...*/ }
62+
void connect();
63+
void disconnect();
64+
65+
UserAccount readFromDb(String userId);
66+
UserAccount writeToDb(UserAccount userAccount);
67+
UserAccount updateDb(UserAccount userAccount);
68+
UserAccount upsertDb(UserAccount userAccount);
7969
}
8070
```
8171

@@ -171,30 +161,43 @@ strategies.
171161
@Slf4j
172162
public class CacheStore {
173163

164+
private static final int CAPACITY = 3;
174165
private static LruCache cache;
166+
private final DbManager dbManager;
175167

176168
/* ... details omitted ... */
177169

178-
public static UserAccount readThrough(String userId) {
170+
public UserAccount readThrough(final String userId) {
179171
if (cache.contains(userId)) {
180-
LOGGER.info("# Cache Hit!");
172+
LOGGER.info("# Found in Cache!");
181173
return cache.get(userId);
182174
}
183-
LOGGER.info("# Cache Miss!");
184-
UserAccount userAccount = DbManager.readFromDb(userId);
175+
LOGGER.info("# Not found in cache! Go to DB!!");
176+
UserAccount userAccount = dbManager.readFromDb(userId);
185177
cache.set(userId, userAccount);
186178
return userAccount;
187179
}
188180

189-
public static void writeThrough(UserAccount userAccount) {
181+
public void writeThrough(final UserAccount userAccount) {
190182
if (cache.contains(userAccount.getUserId())) {
191-
DbManager.updateDb(userAccount);
183+
dbManager.updateDb(userAccount);
192184
} else {
193-
DbManager.writeToDb(userAccount);
185+
dbManager.writeToDb(userAccount);
194186
}
195187
cache.set(userAccount.getUserId(), userAccount);
196188
}
197189

190+
public void writeAround(final UserAccount userAccount) {
191+
if (cache.contains(userAccount.getUserId())) {
192+
dbManager.updateDb(userAccount);
193+
// Cache data has been updated -- remove older
194+
cache.invalidate(userAccount.getUserId());
195+
// version from cache.
196+
} else {
197+
dbManager.writeToDb(userAccount);
198+
}
199+
}
200+
198201
public static void clearCache() {
199202
if (cache != null) {
200203
cache.clear();
@@ -225,34 +228,39 @@ class.
225228
public final class AppManager {
226229

227230
private static CachingPolicy cachingPolicy;
231+
private final DbManager dbManager;
232+
private final CacheStore cacheStore;
228233

229234
private AppManager() {
230235
}
231236

232-
public static void initDb(boolean useMongoDb) { /* ... */ }
237+
public void initDb() { /* ... */ }
233238

234239
public static void initCachingPolicy(CachingPolicy policy) { /* ... */ }
235240

236241
public static void initCacheCapacity(int capacity) { /* ... */ }
237242

238-
public static UserAccount find(String userId) {
239-
if (cachingPolicy == CachingPolicy.THROUGH || cachingPolicy == CachingPolicy.AROUND) {
240-
return CacheStore.readThrough(userId);
243+
public UserAccount find(final String userId) {
244+
LOGGER.info("Trying to find {} in cache", userId);
245+
if (cachingPolicy == CachingPolicy.THROUGH
246+
|| cachingPolicy == CachingPolicy.AROUND) {
247+
return cacheStore.readThrough(userId);
241248
} else if (cachingPolicy == CachingPolicy.BEHIND) {
242-
return CacheStore.readThroughWithWriteBackPolicy(userId);
249+
return cacheStore.readThroughWithWriteBackPolicy(userId);
243250
} else if (cachingPolicy == CachingPolicy.ASIDE) {
244251
return findAside(userId);
245252
}
246253
return null;
247254
}
248255

249-
public static void save(UserAccount userAccount) {
256+
public void save(final UserAccount userAccount) {
257+
LOGGER.info("Save record!");
250258
if (cachingPolicy == CachingPolicy.THROUGH) {
251-
CacheStore.writeThrough(userAccount);
259+
cacheStore.writeThrough(userAccount);
252260
} else if (cachingPolicy == CachingPolicy.AROUND) {
253-
CacheStore.writeAround(userAccount);
261+
cacheStore.writeAround(userAccount);
254262
} else if (cachingPolicy == CachingPolicy.BEHIND) {
255-
CacheStore.writeBehind(userAccount);
263+
cacheStore.writeBehind(userAccount);
256264
} else if (cachingPolicy == CachingPolicy.ASIDE) {
257265
saveAside(userAccount);
258266
}
@@ -272,24 +280,35 @@ Here is what we do in the main class of the application.
272280
@Slf4j
273281
public class App {
274282

275-
public static void main(String[] args) {
276-
AppManager.initDb(false);
277-
AppManager.initCacheCapacity(3);
278-
var app = new App();
283+
public static void main(final String[] args) {
284+
boolean isDbMongo = isDbMongo(args);
285+
if(isDbMongo){
286+
LOGGER.info("Using the Mongo database engine to run the application.");
287+
} else {
288+
LOGGER.info("Using the 'in Memory' database to run the application.");
289+
}
290+
App app = new App(isDbMongo);
279291
app.useReadAndWriteThroughStrategy();
292+
String splitLine = "==============================================";
293+
LOGGER.info(splitLine);
280294
app.useReadThroughAndWriteAroundStrategy();
295+
LOGGER.info(splitLine);
281296
app.useReadThroughAndWriteBehindStrategy();
297+
LOGGER.info(splitLine);
282298
app.useCacheAsideStategy();
299+
LOGGER.info(splitLine);
283300
}
284301

285302
public void useReadAndWriteThroughStrategy() {
286303
LOGGER.info("# CachingPolicy.THROUGH");
287-
AppManager.initCachingPolicy(CachingPolicy.THROUGH);
304+
appManager.initCachingPolicy(CachingPolicy.THROUGH);
305+
288306
var userAccount1 = new UserAccount("001", "John", "He is a boy.");
289-
AppManager.save(userAccount1);
290-
LOGGER.info(AppManager.printCacheContent());
291-
AppManager.find("001");
292-
AppManager.find("001");
307+
308+
appManager.save(userAccount1);
309+
LOGGER.info(appManager.printCacheContent());
310+
appManager.find("001");
311+
appManager.find("001");
293312
}
294313

295314
public void useReadThroughAndWriteAroundStrategy() { /* ... */ }
@@ -300,16 +319,6 @@ public class App {
300319
}
301320
```
302321

303-
Finally, here is some of the console output from the program.
304-
305-
```
306-
12:32:53.845 [main] INFO com.iluwatar.caching.App - # CachingPolicy.THROUGH
307-
12:32:53.900 [main] INFO com.iluwatar.caching.App -
308-
--CACHE CONTENT--
309-
UserAccount(userId=001, userName=John, additionalInfo=He is a boy.)
310-
----
311-
```
312-
313322
## Class diagram
314323

315324
![alt text](./etc/caching.png "Caching")

caching/docker-compose.yml

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
version: '3.7'
2+
services:
3+
mongodb_container:
4+
image: mongo:latest
5+
environment:
6+
MONGO_INITDB_ROOT_USERNAME: root
7+
MONGO_INITDB_ROOT_PASSWORD: rootpassword
8+
ports:
9+
- 27017:27017
10+
volumes:
11+
- ./mongo-data/:/data/db

caching/etc/caching.png

-112 KB
Binary file not shown.

caching/pom.xml

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -39,19 +39,21 @@
3939
<scope>test</scope>
4040
</dependency>
4141
<dependency>
42-
<groupId>org.mongodb</groupId>
43-
<artifactId>mongodb-driver</artifactId>
44-
<version>3.12.1</version>
42+
<groupId>org.mockito</groupId>
43+
<artifactId>mockito-junit-jupiter</artifactId>
44+
<version>3.12.4</version>
45+
<scope>test</scope>
4546
</dependency>
4647
<dependency>
47-
<groupId>org.mongodb</groupId>
48-
<artifactId>mongodb-driver-core</artifactId>
49-
<version>3.0.4</version>
48+
<groupId>org.mockito</groupId>
49+
<artifactId>mockito-all</artifactId>
50+
<version>1.10.19</version>
51+
<scope>test</scope>
5052
</dependency>
5153
<dependency>
5254
<groupId>org.mongodb</groupId>
53-
<artifactId>bson</artifactId>
54-
<version>3.0.4</version>
55+
<artifactId>mongo-java-driver</artifactId>
56+
<version>3.4.1</version>
5557
</dependency>
5658
</dependencies>
5759
<!--

0 commit comments

Comments
 (0)