1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.syncope.client.console.rest;
20
21 import java.io.IOException;
22 import java.io.InputStream;
23 import java.util.ArrayList;
24 import java.util.LinkedHashMap;
25 import java.util.List;
26 import java.util.Map;
27 import javax.ws.rs.core.GenericType;
28 import javax.ws.rs.core.HttpHeaders;
29 import javax.ws.rs.core.Response;
30 import org.apache.commons.lang3.StringUtils;
31 import org.apache.cxf.jaxrs.client.Client;
32 import org.apache.cxf.jaxrs.client.WebClient;
33 import org.apache.syncope.client.lib.batch.BatchRequest;
34 import org.apache.syncope.client.ui.commons.status.StatusBean;
35 import org.apache.syncope.client.ui.commons.status.StatusUtils;
36 import org.apache.syncope.common.lib.request.ResourceAR;
37 import org.apache.syncope.common.lib.request.ResourceDR;
38 import org.apache.syncope.common.lib.request.StatusR;
39 import org.apache.syncope.common.lib.to.AnyTO;
40 import org.apache.syncope.common.lib.to.ProvisioningResult;
41 import org.apache.syncope.common.lib.types.ResourceAssociationAction;
42 import org.apache.syncope.common.lib.types.ResourceDeassociationAction;
43 import org.apache.syncope.common.lib.types.StatusRType;
44 import org.apache.syncope.common.rest.api.RESTHeaders;
45 import org.apache.syncope.common.rest.api.batch.BatchPayloadParser;
46 import org.apache.syncope.common.rest.api.batch.BatchRequestItem;
47 import org.apache.syncope.common.rest.api.batch.BatchResponseItem;
48 import org.apache.syncope.common.rest.api.service.AnyService;
49 import org.apache.wicket.extensions.markup.html.repeater.util.SortParam;
50
51 public abstract class AbstractAnyRestClient<TO extends AnyTO> extends BaseRestClient {
52
53 private static final long serialVersionUID = 1962529678091410544L;
54
55 protected abstract Class<? extends AnyService<TO>> getAnyServiceClass();
56
57 public abstract int count(String realm, String fiql, String type);
58
59 public abstract List<TO> search(String realm, String fiql, int page, int size, SortParam<String> sort, String type);
60
61 public TO read(final String key) {
62 return getService(getAnyServiceClass()).read(key);
63 }
64
65 public ProvisioningResult<TO> delete(final String etag, final String key) {
66 ProvisioningResult<TO> result;
67 synchronized (this) {
68 result = getService(etag, getAnyServiceClass()).delete(key).
69 readEntity(new GenericType<>() {
70 });
71 resetClient(getAnyServiceClass());
72 }
73 return result;
74 }
75
76 protected List<BatchResponseItem> parseBatchResponse(final Response response) throws IOException {
77 return BatchPayloadParser.parse(
78 (InputStream) response.getEntity(), response.getMediaType(), new BatchResponseItem());
79 }
80
81 public Map<String, String> associate(
82 final ResourceAssociationAction action,
83 final String etag,
84 final String key,
85 final List<StatusBean> statuses) {
86
87 Map<String, String> result = new LinkedHashMap<>();
88 synchronized (this) {
89 AnyService<?> service = getService(etag, getAnyServiceClass());
90 Client client = WebClient.client(service);
91 List<String> accept = client.getHeaders().get(HttpHeaders.ACCEPT);
92 if (!accept.contains(RESTHeaders.MULTIPART_MIXED)) {
93 client.accept(RESTHeaders.MULTIPART_MIXED);
94 }
95
96 StatusR statusR = StatusUtils.statusR(key, StatusRType.ACTIVATE, statuses);
97
98 ResourceAR resourceAR = new ResourceAR.Builder().key(key).
99 action(action).
100 onSyncope(statusR.isOnSyncope()).
101 resources(statusR.getResources()).build();
102 try {
103 List<BatchResponseItem> items = parseBatchResponse(service.associate(resourceAR));
104 for (int i = 0; i < items.size(); i++) {
105 result.put(
106 resourceAR.getResources().get(i),
107 getStatus(items.get(i).getStatus()));
108 }
109 } catch (IOException e) {
110 LOG.error("While processing Batch response", e);
111 }
112
113 resetClient(getAnyServiceClass());
114 }
115 return result;
116 }
117
118 public Map<String, String> deassociate(
119 final ResourceDeassociationAction action,
120 final String etag,
121 final String key,
122 final List<StatusBean> statuses) {
123
124 Map<String, String> result = new LinkedHashMap<>();
125 synchronized (this) {
126 AnyService<?> service = getService(etag, getAnyServiceClass());
127 Client client = WebClient.client(service);
128 List<String> accept = client.getHeaders().get(HttpHeaders.ACCEPT);
129 if (!accept.contains(RESTHeaders.MULTIPART_MIXED)) {
130 client.accept(RESTHeaders.MULTIPART_MIXED);
131 }
132
133 ResourceDR resourceDR = new ResourceDR.Builder().key(key).
134 action(action).
135 resources(StatusUtils.statusR(key, StatusRType.ACTIVATE, statuses).getResources()).build();
136 try {
137 List<BatchResponseItem> items = parseBatchResponse(service.deassociate(resourceDR));
138 for (int i = 0; i < items.size(); i++) {
139 result.put(
140 resourceDR.getResources().get(i),
141 getStatus(items.get(i).getStatus()));
142 }
143 } catch (IOException e) {
144 LOG.error("While processing Batch response", e);
145 }
146
147 resetClient(getAnyServiceClass());
148 }
149 return result;
150 }
151
152 public Map<String, String> batch(final BatchRequest batchRequest) {
153 List<BatchRequestItem> batchRequestItems = new ArrayList<>(batchRequest.getItems());
154
155 Map<String, String> result = new LinkedHashMap<>();
156 try {
157 List<BatchResponseItem> batchResponseItems = batchRequest.commit().getItems();
158 for (int i = 0; i < batchResponseItems.size(); i++) {
159 String status = getStatus(batchResponseItems.get(i).getStatus());
160 if (batchRequestItems.get(i).getRequestURI().endsWith("/status")) {
161 result.put(StringUtils.substringAfterLast(
162 StringUtils.substringBefore(batchRequestItems.get(i).getRequestURI(), "/status"), "/"),
163 status);
164 } else {
165 result.put(StringUtils.substringAfterLast(
166 batchRequestItems.get(i).getRequestURI(), "/"), status);
167 }
168 }
169 } catch (IOException e) {
170 LOG.error("While processing Batch response", e);
171 }
172
173 return result;
174 }
175 }