1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package info.magnolia.ui.chooser.definition;
35
36 import info.magnolia.config.MutableWrapper;
37 import info.magnolia.config.Mutator;
38 import info.magnolia.config.registry.DefinitionProvider;
39 import info.magnolia.dynamic.MagnoliaProxy;
40 import info.magnolia.i18nsystem.I18nizer;
41 import info.magnolia.i18nsystem.SimpleTranslator;
42 import info.magnolia.objectfactory.Components;
43 import info.magnolia.ui.api.app.AppDescriptor;
44 import info.magnolia.ui.api.app.registry.AppDescriptorRegistry;
45 import info.magnolia.ui.contentapp.configuration.BrowserDescriptor;
46 import info.magnolia.ui.contentapp.configuration.ContentViewDefinition;
47 import info.magnolia.ui.contentapp.configuration.GridViewDefinition;
48 import info.magnolia.ui.contentapp.configuration.WorkbenchDefinition;
49 import info.magnolia.ui.contentapp.configuration.column.ColumnDefinition;
50 import info.magnolia.ui.contentapp.configuration.column.ColumnDefinitionMutator;
51 import info.magnolia.ui.datasource.WithDatasource;
52 import info.magnolia.ui.field.TextFieldDefinition;
53 import info.magnolia.ui.datasource.DatasourceDefinition;
54
55 import java.util.List;
56 import java.util.Objects;
57 import java.util.Optional;
58
59 import lombok.AccessLevel;
60 import lombok.Getter;
61 import lombok.Setter;
62
63
64
65
66
67
68 @Getter
69 @Setter
70 public class AppAwareWorkbenchChooserDefinition<T> extends WorkbenchChooserDefinition<T> {
71
72 private String title;
73 private String appName;
74 private WorkbenchDefinition<T> workbenchDefinition;
75
76 @Getter(AccessLevel.PROTECTED)
77 @Setter(AccessLevel.PRIVATE)
78 private AppDescriptorRegistry appDescriptorRegistry;
79 private final I18nizer i18nizer;
80
81 public AppAwareWorkbenchChooserDefinition() {
82 super();
83 this.appDescriptorRegistry = Components.getComponent(AppDescriptorRegistry.class);
84 this.i18nizer = Components.getComponent(I18nizer.class);
85 }
86
87
88
89
90
91
92
93 @Override
94 public DatasourceDefinition getDatasource() {
95 return Optional.ofNullable(super.getDatasource()).orElseGet(() -> resolveDatasourceFromAppName().orElse(null));
96 }
97
98 private Optional<DatasourceDefinition> resolveDatasourceFromAppName() {
99 return Optional.of((DatasourceDefinition) resolveBrowserDescriptorFromAppName()
100 .map(BrowserDescriptor::getDatasource)
101 .orElseGet(() -> {
102 AppDescriptor appDescriptor = getAppDescriptorRegistry().getProvider(getAppName()).get();
103 return Optional.of(appDescriptor)
104 .filter(WithDatasource.class::isInstance)
105 .map(WithDatasource.class::cast)
106 .map(WithDatasource::getDatasource)
107 .get();
108 }));
109 }
110
111 @Override
112 public WorkbenchDefinition<T> getWorkbench() {
113 WorkbenchDefinition<T> workbenchFromAppOrDefault = resolveWorkbenchDefinitionFromAppName().orElse(super.getWorkbench());
114 final WorkbenchDefinition<T> workbenchDefinition = Optional.ofNullable(this.workbenchDefinition).orElse(workbenchFromAppOrDefault);
115 final WorkbenchDefinition<T> wrapped = MutableWrapper.wrap(workbenchDefinition);
116 wrapped.getContentViews()
117 .forEach(view -> {
118 applySingleSelectAndReadOnly(view);
119 autogenerateTextFilterComponent(view);
120 });
121 return wrapped;
122 }
123
124 private void applySingleSelectAndReadOnly(ContentViewDefinition<T> viewDefinition) {
125 final TabularViewMutator tabularViewMutator = new TabularViewMutator<>(MutableWrapper.asMutable(viewDefinition));
126 if (!this.isMultiSelect()) {
127 tabularViewMutator.setSingleSelectMode();
128 }
129 tabularViewMutator.setReadOnly();
130 }
131
132 private void autogenerateTextFilterComponent(ContentViewDefinition<T> viewDefinition) {
133 Class<?> viewDefClass = viewDefinition.getClass();
134 while(MagnoliaProxy.class.isAssignableFrom(viewDefClass)) {
135 viewDefClass = viewDefinition.getClass().getSuperclass();
136 }
137
138 if (GridViewDefinition.class.isAssignableFrom(viewDefClass)) {
139 TextFieldDefinitioneldDefinition">TextFieldDefinition defaultFilterComponent = new TextFieldDefinition();
140 SimpleTranslator translator = Components.getComponent(SimpleTranslator.class);
141 defaultFilterComponent.setPlaceholder(translator.translate("dialogs.chooseDialog.filter.search"));
142
143 List<ColumnDefinition<T>> columns = ((GridViewDefinition<T>) viewDefinition).getColumns();
144 columns.stream()
145 .filter(columnDefinition -> Objects.isNull(columnDefinition.getFilterComponent()))
146 .filter(columnDefinition -> String.class.isAssignableFrom(columnDefinition.getType()))
147 .map(columnDefinition -> new ColumnDefinitionMutator<>(MutableWrapper.asMutable(columnDefinition)))
148 .forEach(mutator -> mutator.setFilterComponent(defaultFilterComponent));
149 }
150 }
151
152 private Optional<WorkbenchDefinition<T>> resolveWorkbenchDefinitionFromAppName() {
153 return resolveBrowserDescriptorFromAppName().map(BrowserDescriptor::getWorkbench);
154 }
155
156 private Optional<BrowserDescriptor> resolveBrowserDescriptorFromAppName() {
157 return Optional.ofNullable(getAppName())
158 .map(appDescriptorRegistry::getProvider)
159 .map(DefinitionProvider::get)
160 .map(i18nizer::decorate)
161 .map(provider -> provider.getSubApps().values()
162 .stream()
163 .filter(BrowserDescriptor.class::isInstance)
164 .map(BrowserDescriptor.class::cast)
165 .findFirst()
166 .orElseThrow(() -> new IllegalStateException("Could not resolve browser descriptor from app " + getAppName()))
167 );
168 }
169
170 private static class TabularViewMutator<T> extends Mutator<ContentViewDefinition<T>> {
171
172 TabularViewMutator(MutableWrapper.Mutable<ContentViewDefinition<T>> mutableObject) {
173 super(mutableObject);
174 }
175
176 void setSingleSelectMode() {
177 setProperty("multiSelect", false);
178 }
179
180 void setReadOnly() {
181 setProperty("readOnly", true);
182 }
183 }
184 }