001
014
015 package com.liferay.portlet.dynamicdatalists.util;
016
017 import com.liferay.portal.kernel.json.JSONArray;
018 import com.liferay.portal.kernel.json.JSONFactoryUtil;
019 import com.liferay.portal.kernel.json.JSONObject;
020 import com.liferay.portal.kernel.language.LanguageUtil;
021 import com.liferay.portal.kernel.log.Log;
022 import com.liferay.portal.kernel.log.LogFactoryUtil;
023 import com.liferay.portal.kernel.repository.model.FileEntry;
024 import com.liferay.portal.kernel.search.Hits;
025 import com.liferay.portal.kernel.search.Indexer;
026 import com.liferay.portal.kernel.search.IndexerRegistryUtil;
027 import com.liferay.portal.kernel.templateparser.Transformer;
028 import com.liferay.portal.kernel.util.GetterUtil;
029 import com.liferay.portal.kernel.util.LocaleUtil;
030 import com.liferay.portal.kernel.util.ParamUtil;
031 import com.liferay.portal.kernel.util.StringPool;
032 import com.liferay.portal.kernel.util.StringUtil;
033 import com.liferay.portal.kernel.util.Validator;
034 import com.liferay.portal.kernel.xml.Document;
035 import com.liferay.portal.kernel.xml.Element;
036 import com.liferay.portal.kernel.xml.SAXReaderUtil;
037 import com.liferay.portal.model.Group;
038 import com.liferay.portal.model.PortletConstants;
039 import com.liferay.portal.service.GroupLocalServiceUtil;
040 import com.liferay.portal.service.PortletPreferencesLocalServiceUtil;
041 import com.liferay.portal.service.ServiceContext;
042 import com.liferay.portal.theme.ThemeDisplay;
043 import com.liferay.portal.util.PortletKeys;
044 import com.liferay.portlet.documentlibrary.service.DLAppLocalServiceUtil;
045 import com.liferay.portlet.dynamicdatalists.NoSuchRecordException;
046 import com.liferay.portlet.dynamicdatalists.model.DDLRecord;
047 import com.liferay.portlet.dynamicdatalists.model.DDLRecordConstants;
048 import com.liferay.portlet.dynamicdatalists.model.DDLRecordSet;
049 import com.liferay.portlet.dynamicdatalists.model.DDLRecordVersion;
050 import com.liferay.portlet.dynamicdatalists.service.DDLRecordLocalServiceUtil;
051 import com.liferay.portlet.dynamicdatalists.service.DDLRecordServiceUtil;
052 import com.liferay.portlet.dynamicdatalists.service.DDLRecordSetLocalServiceUtil;
053 import com.liferay.portlet.dynamicdatamapping.model.DDMStructure;
054 import com.liferay.portlet.dynamicdatamapping.model.DDMTemplate;
055 import com.liferay.portlet.dynamicdatamapping.service.DDMTemplateLocalServiceUtil;
056 import com.liferay.portlet.dynamicdatamapping.storage.Field;
057 import com.liferay.portlet.dynamicdatamapping.storage.FieldConstants;
058 import com.liferay.portlet.dynamicdatamapping.storage.Fields;
059 import com.liferay.portlet.dynamicdatamapping.storage.StorageEngineUtil;
060 import com.liferay.portlet.dynamicdatamapping.util.DDMImpl;
061 import com.liferay.portlet.dynamicdatamapping.util.DDMUtil;
062 import com.liferay.portlet.dynamicdatamapping.util.DDMXMLUtil;
063 import com.liferay.portlet.journal.util.JournalUtil;
064 import com.liferay.util.portlet.PortletRequestUtil;
065
066 import java.util.ArrayList;
067 import java.util.Date;
068 import java.util.Iterator;
069 import java.util.List;
070 import java.util.Map;
071
072 import javax.portlet.PortletPreferences;
073 import javax.portlet.RenderRequest;
074 import javax.portlet.RenderResponse;
075
076 import javax.servlet.http.HttpServletRequest;
077 import javax.servlet.http.HttpServletResponse;
078
079
083 public class DDLImpl implements DDL {
084
085 public void addAllReservedEls(
086 Element rootElement, Map<String, String> tokens,
087 DDLRecordSet recordSet) {
088
089 JournalUtil.addReservedEl(
090 rootElement, tokens, DDLConstants.RESERVED_RECORD_SET_ID,
091 String.valueOf(recordSet.getRecordSetId()));
092
093 JournalUtil.addReservedEl(
094 rootElement, tokens, DDLConstants.RESERVED_RECORD_SET_NAME,
095 recordSet.getName());
096
097 JournalUtil.addReservedEl(
098 rootElement, tokens, DDLConstants.RESERVED_RECORD_SET_DESCRIPTION,
099 recordSet.getDescription());
100
101 JournalUtil.addReservedEl(
102 rootElement, tokens, DDLConstants.RESERVED_DDM_STRUCTURE_ID,
103 String.valueOf(recordSet.getDDMStructureId()));
104 }
105
106 public JSONObject getRecordJSONObject(DDLRecord record) throws Exception {
107 return getRecordJSONObject(record, false);
108 }
109
110 public JSONObject getRecordJSONObject(
111 DDLRecord record, boolean latestRecordVersion)
112 throws Exception {
113
114 DDLRecordSet recordSet = record.getRecordSet();
115
116 DDMStructure ddmStructure = recordSet.getDDMStructure();
117
118 JSONObject jsonObject = JSONFactoryUtil.createJSONObject();
119
120 for (String fieldName : ddmStructure.getFieldNames()) {
121 jsonObject.put(fieldName, StringPool.BLANK);
122 }
123
124 jsonObject.put("displayIndex", record.getDisplayIndex());
125 jsonObject.put("recordId", record.getRecordId());
126
127 DDLRecordVersion recordVersion = record.getRecordVersion();
128
129 if (latestRecordVersion) {
130 recordVersion = record.getLatestRecordVersion();
131 }
132
133 Fields fields = StorageEngineUtil.getFields(
134 recordVersion.getDDMStorageId());
135
136 Iterator<Field> itr = fields.iterator();
137
138 while (itr.hasNext()) {
139 Field field = itr.next();
140
141 String fieldName = field.getName();
142 String fieldType = field.getType();
143 Object fieldValue = field.getValue();
144
145 if (fieldValue instanceof Date) {
146 jsonObject.put(fieldName, ((Date)fieldValue).getTime());
147 }
148 else if (fieldType.equals(DDMImpl.TYPE_DDM_DOCUMENTLIBRARY) &&
149 Validator.isNotNull(fieldValue)) {
150
151 JSONObject fieldValueJSONObject =
152 JSONFactoryUtil.createJSONObject(
153 String.valueOf(fieldValue));
154
155 String uuid = fieldValueJSONObject.getString("uuid");
156 long groupId = fieldValueJSONObject.getLong("groupId");
157
158 fieldValueJSONObject.put(
159 "title", getFileEntryTitle(uuid, groupId));
160
161 jsonObject.put(fieldName, fieldValueJSONObject.toString());
162 }
163 else if ((fieldType.equals(DDMImpl.TYPE_RADIO) ||
164 fieldType.equals(DDMImpl.TYPE_SELECT)) &&
165 Validator.isNotNull(fieldValue)) {
166
167 fieldValue = JSONFactoryUtil.createJSONArray(
168 String.valueOf(fieldValue));
169
170 jsonObject.put(fieldName, (JSONArray)fieldValue);
171 }
172 else {
173 jsonObject.put(fieldName, String.valueOf(fieldValue));
174 }
175 }
176
177 return jsonObject;
178 }
179
180 public List<DDLRecord> getRecords(Hits hits) throws Exception {
181 List<DDLRecord> records = new ArrayList<DDLRecord>();
182
183 List<com.liferay.portal.kernel.search.Document> documents =
184 hits.toList();
185
186 for (com.liferay.portal.kernel.search.Document document : documents) {
187 long recordId = GetterUtil.getLong(
188 document.get(
189 com.liferay.portal.kernel.search.Field.ENTRY_CLASS_PK));
190
191 try {
192 DDLRecord record = DDLRecordLocalServiceUtil.getRecord(
193 recordId);
194
195 records.add(record);
196 }
197 catch (NoSuchRecordException nsre) {
198 if (_log.isWarnEnabled()) {
199 _log.warn(
200 "DDL record index is stale and contains record " +
201 recordId);
202 }
203
204 Indexer indexer = IndexerRegistryUtil.getIndexer(
205 DDLRecord.class);
206
207 long companyId = GetterUtil.getLong(
208 document.get(
209 com.liferay.portal.kernel.search.Field.COMPANY_ID));
210
211 indexer.delete(companyId, document.getUID());
212 }
213 }
214
215 return records;
216 }
217
218 public JSONArray getRecordSetJSONArray(DDLRecordSet recordSet)
219 throws Exception {
220
221 JSONArray jsonArray = JSONFactoryUtil.createJSONArray();
222
223 DDMStructure ddmStructure = recordSet.getDDMStructure();
224
225 Map<String, Map<String, String>> fieldsMap =
226 ddmStructure.getFieldsMap();
227
228 for (Map<String, String> fields : fieldsMap.values()) {
229 JSONObject jsonObject = JSONFactoryUtil.createJSONObject();
230
231 String dataType = fields.get(FieldConstants.DATA_TYPE);
232
233 jsonObject.put("dataType", dataType);
234
235 boolean editable = GetterUtil.getBoolean(
236 fields.get(FieldConstants.EDITABLE), true);
237
238 jsonObject.put("editable", editable);
239
240 String label = fields.get(FieldConstants.LABEL);
241
242 jsonObject.put("label", label);
243
244 String name = fields.get(FieldConstants.NAME);
245
246 jsonObject.put("name", name);
247
248 boolean required = GetterUtil.getBoolean(
249 fields.get(FieldConstants.REQUIRED));
250
251 jsonObject.put("required", required);
252
253 boolean sortable = GetterUtil.getBoolean(
254 fields.get(FieldConstants.SORTABLE), true);
255
256 jsonObject.put("sortable", sortable);
257
258 String type = fields.get(FieldConstants.TYPE);
259
260 jsonObject.put("type", type);
261
262 jsonArray.put(jsonObject);
263 }
264
265 return jsonArray;
266 }
267
268 public JSONArray getRecordsJSONArray(DDLRecordSet recordSet)
269 throws Exception {
270
271 return getRecordsJSONArray(recordSet.getRecords(), false);
272 }
273
274 public JSONArray getRecordsJSONArray(List<DDLRecord> records)
275 throws Exception {
276
277 JSONArray jsonArray = JSONFactoryUtil.createJSONArray();
278
279 for (DDLRecord record : records) {
280 JSONObject jsonObject = getRecordJSONObject(record);
281
282 jsonArray.put(jsonObject);
283 }
284
285 return jsonArray;
286 }
287
288 public JSONArray getRecordsJSONArray(
289 List<DDLRecord> records, boolean latestRecordVersion)
290 throws Exception {
291
292 JSONArray jsonArray = JSONFactoryUtil.createJSONArray();
293
294 for (DDLRecord record : records) {
295 JSONObject jsonObject = getRecordJSONObject(
296 record, latestRecordVersion);
297
298 jsonArray.put(jsonObject);
299 }
300
301 return jsonArray;
302 }
303
304 public String getTemplateContent(
305 long ddmTemplateId, DDLRecordSet recordSet,
306 ThemeDisplay themeDisplay, RenderRequest renderRequest,
307 RenderResponse renderResponse)
308 throws Exception {
309
310 String viewMode = ParamUtil.getString(renderRequest, "viewMode");
311
312 String languageId = LanguageUtil.getLanguageId(renderRequest);
313
314 String xmlRequest = PortletRequestUtil.toXML(
315 renderRequest, renderResponse);
316
317 if (Validator.isNull(xmlRequest)) {
318 xmlRequest = "<request />";
319 }
320
321 Map<String, String> tokens = JournalUtil.getTokens(
322 recordSet.getGroupId(), themeDisplay, xmlRequest);
323
324 tokens.put("template_id", StringUtil.valueOf(ddmTemplateId));
325
326 String xml = StringPool.BLANK;
327
328 Document document = SAXReaderUtil.createDocument();
329
330 Element rootElement = document.addElement("root");
331
332 Document requestDocument = SAXReaderUtil.read(xmlRequest);
333
334 rootElement.add(requestDocument.getRootElement().createCopy());
335
336 addAllReservedEls(rootElement, tokens, recordSet);
337
338 xml = DDMXMLUtil.formatXML(document);
339
340 DDMTemplate template = DDMTemplateLocalServiceUtil.getTemplate(
341 ddmTemplateId);
342
343 return _transformer.transform(
344 themeDisplay, tokens, viewMode, languageId, xml,
345 template.getScript(), template.getLanguage());
346 }
347
348 public boolean isEditable(
349 HttpServletRequest request, String portletId, long groupId)
350 throws Exception {
351
352 boolean defaultValue = ParamUtil.getBoolean(request, "editable", true);
353
354 return isEditable(portletId, groupId, defaultValue);
355 }
356
357 public boolean isEditable(
358 PortletPreferences preferences, String portletId, long groupId)
359 throws Exception {
360
361 boolean defaultValue = GetterUtil.getBoolean(
362 preferences.getValue("editable", null), true);
363
364 return isEditable(portletId, groupId, defaultValue);
365 }
366
367 public void sendRecordFileUpload(
368 HttpServletRequest request, HttpServletResponse response,
369 DDLRecord record, String fieldName, int valueIndex)
370 throws Exception {
371
372 Field field = record.getField(fieldName);
373
374 DDMUtil.sendFieldFile(request, response, field, valueIndex);
375 }
376
377 public void sendRecordFileUpload(
378 HttpServletRequest request, HttpServletResponse response,
379 long recordId, String fieldName, int valueIndex)
380 throws Exception {
381
382 DDLRecord record = DDLRecordServiceUtil.getRecord(recordId);
383
384 sendRecordFileUpload(request, response, record, fieldName, valueIndex);
385 }
386
387 public DDLRecord updateRecord(
388 long recordId, long recordSetId, boolean mergeFields,
389 boolean checkPermission, ServiceContext serviceContext)
390 throws Exception {
391
392 DDLRecord record = DDLRecordLocalServiceUtil.fetchRecord(recordId);
393
394 PortletPreferences preferences =
395 PortletPreferencesLocalServiceUtil.getPreferences(
396 serviceContext.getPortletPreferencesIds());
397
398 if (!isEditable(
399 preferences, serviceContext.getPortletId(),
400 serviceContext.getScopeGroupId())) {
401
402 return record;
403 }
404
405 boolean majorVersion = ParamUtil.getBoolean(
406 serviceContext, "majorVersion");
407
408 DDLRecordSet recordSet = DDLRecordSetLocalServiceUtil.getDDLRecordSet(
409 recordSetId);
410
411 DDMStructure ddmStructure = recordSet.getDDMStructure();
412
413 Fields fields = DDMUtil.getFields(
414 ddmStructure.getStructureId(), serviceContext);
415
416 if (record != null) {
417 if (checkPermission) {
418 record = DDLRecordServiceUtil.updateRecord(
419 recordId, majorVersion,
420 DDLRecordConstants.DISPLAY_INDEX_DEFAULT, fields,
421 mergeFields, serviceContext);
422 }
423 else {
424 record = DDLRecordLocalServiceUtil.updateRecord(
425 serviceContext.getUserId(), recordId, majorVersion,
426 DDLRecordConstants.DISPLAY_INDEX_DEFAULT, fields,
427 mergeFields, serviceContext);
428 }
429 }
430 else {
431 if (checkPermission) {
432 record = DDLRecordServiceUtil.addRecord(
433 serviceContext.getScopeGroupId(), recordSetId,
434 DDLRecordConstants.DISPLAY_INDEX_DEFAULT, fields,
435 serviceContext);
436 }
437 else {
438 record = DDLRecordLocalServiceUtil.addRecord(
439 serviceContext.getUserId(),
440 serviceContext.getScopeGroupId(), recordSetId,
441 DDLRecordConstants.DISPLAY_INDEX_DEFAULT, fields,
442 serviceContext);
443 }
444
445 }
446
447 uploadRecordFieldFiles(record, serviceContext);
448
449 return record;
450 }
451
452 public DDLRecord updateRecord(
453 long recordId, long recordSetId, boolean mergeFields,
454 ServiceContext serviceContext)
455 throws Exception {
456
457 return updateRecord(
458 recordId, recordSetId, mergeFields, true, serviceContext);
459 }
460
461 public void uploadRecordFieldFile(
462 DDLRecord record, String fieldName, ServiceContext serviceContext)
463 throws Exception {
464
465 DDLRecordSet recordSet = record.getRecordSet();
466
467 DDMStructure ddmStructure = recordSet.getDDMStructure();
468
469 DDLRecordVersion recordVersion = record.getLatestRecordVersion();
470
471 DDMUtil.uploadFieldFile(
472 ddmStructure.getStructureId(), recordVersion.getDDMStorageId(),
473 record, fieldName, serviceContext);
474 }
475
476 protected String getFileEntryTitle(String uuid, long groupId) {
477 try {
478 FileEntry fileEntry =
479 DLAppLocalServiceUtil.getFileEntryByUuidAndGroupId(
480 uuid, groupId);
481
482 return fileEntry.getTitle();
483 }
484 catch (Exception e) {
485 return LanguageUtil.format(
486 LocaleUtil.getDefault(), "is-temporarily-unavailable",
487 "content");
488 }
489 }
490
491 protected boolean isEditable(
492 String portletId, long groupId, boolean defaultValue)
493 throws Exception {
494
495 String rootPortletId = PortletConstants.getRootPortletId(portletId);
496
497 if (rootPortletId.equals(PortletKeys.DYNAMIC_DATA_LISTS)) {
498 return true;
499 }
500
501 Group group = GroupLocalServiceUtil.fetchGroup(groupId);
502
503 if ((group == null) || group.isInStagingPortlet(portletId)) {
504 return false;
505 }
506
507 return defaultValue;
508 }
509
510 protected void uploadRecordFieldFiles(
511 DDLRecord record, ServiceContext serviceContext)
512 throws Exception {
513
514 DDLRecordSet recordSet = record.getRecordSet();
515
516 DDMStructure ddmStructure = recordSet.getDDMStructure();
517
518 for (String fieldName : ddmStructure.getFieldNames()) {
519 String fieldDataType = ddmStructure.getFieldDataType(fieldName);
520
521 if (fieldDataType.equals(FieldConstants.FILE_UPLOAD)) {
522 uploadRecordFieldFile(record, fieldName, serviceContext);
523 }
524 }
525 }
526
527 private static Log _log = LogFactoryUtil.getLog(DDLImpl.class);
528
529 private Transformer _transformer = new DDLTransformer();
530
531 }