View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  
20  package org.apache.myfaces.tobago.context;
21  
22  import org.apache.myfaces.tobago.exception.TobagoConfigurationException;
23  import org.slf4j.Logger;
24  import org.slf4j.LoggerFactory;
25  
26  import java.io.Serializable;
27  import java.lang.invoke.MethodHandles;
28  import java.util.ArrayList;
29  import java.util.List;
30  
31  /**
32   * Manages the script and style files for production and development stage.
33   *
34   * @since 1.5.0
35   */
36  public final class ThemeResources implements Serializable {
37  
38    private static final Logger LOG = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
39  
40    /**
41     * @deprecated since 5.0.0
42     */
43    @Deprecated
44    private boolean production;
45  
46    private final List<ThemeScript> includeScripts = new ArrayList<>();
47    private final List<ThemeScript> excludeScripts = new ArrayList<>();
48    private final List<ThemeStyle> includeStyles = new ArrayList<>();
49    private final List<ThemeStyle> excludeStyles = new ArrayList<>();
50  
51    public ThemeResources() {
52    }
53  
54    /**
55     * @deprecated since 5.0.0
56     */
57    @Deprecated
58    public ThemeResources(final boolean production) {
59      this.production = production;
60    }
61  
62    /**
63     * @deprecated since 5.0.0, use static {@link #merge}
64     */
65    @Deprecated
66    public void merge(final ThemeResources fallback) {
67      if (this == fallback) {
68        return;
69      }
70      for (int i = fallback.includeScripts.size() - 1; i >= 0; i--) {
71        final ThemeScript script = fallback.includeScripts.get(i);
72        includeScripts.remove(script);
73        if (!excludeScripts.contains(script)) {
74          includeScripts.add(0, script);
75        }
76      }
77      for (int i = fallback.includeStyles.size() - 1; i >= 0; i--) {
78        final ThemeStyle style = fallback.includeStyles.get(i);
79        includeStyles.remove(style);
80        if (!excludeStyles.contains(style)) {
81          includeStyles.add(0, style);
82        }
83      }
84    }
85  
86    /**
87     * @since 5.0.0
88     */
89    public static ThemeResources merge(final ThemeResources base, final ThemeResources add) {
90      if (base.production != add.production) {
91        throw new TobagoConfigurationException("Resources mismatch!");
92      }
93      final ThemeResources result = new ThemeResources(base.production);
94  
95      for (ThemeScript includeScript : base.includeScripts) {
96        if (!add.excludeScripts.contains(includeScript)) {
97          result.addIncludeScript(includeScript);
98        }
99      }
100     for (ThemeScript includeScript : add.includeScripts) {
101       result.addIncludeScript(includeScript);
102     }
103 
104     for (ThemeStyle includeStyle : base.includeStyles) {
105       if (!add.excludeStyles.contains(includeStyle)) {
106         result.addIncludeStyle(includeStyle);
107       }
108     }
109     for (ThemeStyle includeStyle : add.includeStyles) {
110       result.addIncludeStyle(includeStyle);
111     }
112 
113     return result;
114   }
115 
116   /**
117    * @deprecated since 5.0.0
118    */
119   @Deprecated
120   public boolean isProduction() {
121     return production;
122   }
123 
124   /**
125    * @since 5.0.0
126    */
127   public boolean addIncludeScript(final ThemeScript script) {
128     for (ThemeScript resource : includeScripts) {
129       if (resource.getName().equals(script.getName())) {
130         LOG.warn("Overwriting include script '{}'", script.getName());
131         includeScripts.remove(resource);
132         break;
133       }
134     }
135     return includeScripts.add(script);
136   }
137 
138   /**
139    * @since 5.0.0
140    */
141   public boolean addExcludeScript(final ThemeScript script) {
142     for (ThemeScript resource : excludeScripts) {
143       if (resource.getName().equals(script.getName())) {
144         LOG.warn("Overwriting exclude script '{}'", script.getName());
145         includeScripts.remove(resource);
146         break;
147       }
148     }
149     return excludeScripts.add(script);
150   }
151 
152   /**
153    * @deprecated since 5.0.0, use {@link #addIncludeScript} or {@link #addExcludeScript}
154    */
155   @Deprecated
156   public boolean addScript(final ThemeScript script, final boolean exclude) {
157     return exclude ? addExcludeScript(script) : addIncludeScript(script);
158   }
159 
160   /**
161    * @since 5.0.0
162    */
163   public boolean addIncludeStyle(final ThemeStyle style) {
164     for (ThemeStyle resource : includeStyles) {
165       if (resource.getName().equals(style.getName())) {
166         LOG.warn("Overwriting include style '{}'", style.getName());
167         includeStyles.remove(resource);
168         break;
169       }
170     }
171     return includeStyles.add(style);
172   }
173 
174   /**
175    * @since 5.0.0
176    */
177   public boolean addExcludeStyle(final ThemeStyle style) {
178     for (ThemeStyle resource : excludeStyles) {
179       if (resource.getName().equals(style.getName())) {
180         LOG.warn("Overwriting exclude style '{}'", style.getName());
181         includeStyles.remove(resource);
182         break;
183       }
184     }
185     return excludeStyles.add(style);
186   }
187 
188   /**
189    * @deprecated since 5.0.0, use {@link #addIncludeStyle} or {@link #addExcludeStyle}
190    */
191   @Deprecated
192   public boolean addStyle(final ThemeStyle style, final boolean exclude) {
193     return exclude ? addExcludeStyle(style) : addIncludeStyle(style);
194   }
195 
196   public List<ThemeScript> getScriptList() {
197     return includeScripts;
198   }
199 
200   public List<ThemeStyle> getStyleList() {
201     return includeStyles;
202   }
203 }