Ранее мы использовали шаблон фасада для взаимодействия с унаследованным приложением. Наш следующий шаблон будет шаблон прокси.
Шаблон прокси используется, когда мы хотим
- Контролировать доступ к объекту
- Добавить дополнительную функциональность при доступе к объекту.
Одно из самых распространенных применений — это когда мы хотим отслеживать конкретные действия и добавлять некоторые показатели.
Например, у нас есть служба загрузки данных.
1
2
3
4
5
6
7
|
package com.gkatzioura.design.structural.proxy; public interface DataUploadService { void upload(String payload); } |
И его реализация http
01
02
03
04
05
06
07
08
09
10
|
package com.gkatzioura.design.structural.proxy; public class HttpDataUploadImpl implements DataUploadService { @Override public void upload(String payload) { } } |
Нам необходимо принять некоторые меры в среднем времени, необходимом для отправки полезной нагрузки нашего приложения, чтобы решить, достаточно ли хороша наша реализация. Если нет, возможно, нам нужно рассмотреть что-то более производительное.
Вместо того, чтобы возиться с нашей реализацией и добавлять код, который не имеет ничего общего с фактической передачей полезной нагрузки, мы создадим прокси нашей реализации.
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
|
package com.gkatzioura.design.structural.proxy; import java.nio.charset.Charset; import java.time.Duration; import java.time.Instant; public class HttpDataUploadProxy implements DataUploadService { private final HttpDataUploadImpl httpDataUpload; public HttpDataUploadProxy(HttpDataUploadImpl httpDataUpload) { this .httpDataUpload = httpDataUpload; } @Override public void upload(String payload) { Instant start = Instant.now(); httpDataUpload.upload(payload); Duration duration = Duration.between(start,Instant.now()); int byteSize = payload.getBytes(Charset.defaultCharset()).length; /** * Log properly to splunk, cloudwatch etc */ } } |
Как вы видите, наша реализация не изменилась, и нам удается отправить метрики, необходимые для выбранной вами аналитической службы.
Мы также можем применить тот же шаблон в случае, если эта служба имеет некоторую квоту, и поэтому мы хотим контролировать ее, потому что это может привести к превышению бюджета.
01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
|
package com.gkatzioura.design.structural.proxy; public class HttpDataUploadQuotaProxy implements DataUploadService { private final HttpDataUploadImpl httpDataUpload; public HttpDataUploadQuotaProxy(HttpDataUploadImpl httpDataUpload) { this .httpDataUpload = httpDataUpload; } @Override public void upload(String payload) { if (quotaExceeded()) { throw new IllegalStateException( "Quota exceeded cannot upload payload" ); } httpDataUpload.upload(payload); } private boolean quotaExceeded() { /** * Code that should check whether we exceeded our quota or not */ return false ; } } |
Подводя итог, мы просто использовали шаблон прокси для управления доступом к нашему объекту, а также для улучшения его функциональности.
Вы также можете найти исходный код на github .
Опубликовано на Java Code Geeks с разрешения Эммануила Гкациоураса, партнера нашей программы JCG. Смотрите оригинальную статью здесь: Структурные шаблоны проектирования: Proxy Pattern
Мнения, высказанные участниками Java Code Geeks, являются их собственными. |