1 package org.andromda.core.translation.library;
2
3 import java.util.ArrayList;
4 import java.util.Collection;
5 import java.util.Iterator;
6 import java.util.LinkedHashMap;
7 import java.util.Map;
8
9 import org.andromda.core.common.ExceptionUtils;
10 import org.andromda.core.translation.TranslationUtils;
11 import org.apache.commons.lang.StringUtils;
12 import org.apache.commons.lang.builder.ToStringBuilder;
13
14
15 /***
16 * Represents a translation XML template found within a translation library.
17 *
18 * @author Chad Brandon
19 */
20 public class Translation
21 {
22 private String name;
23 private final Map fragments = new LinkedHashMap();
24 private final Collection ignorePatterns = new ArrayList();
25 private Collection validatePatterns;
26
27 /***
28 * The library translation to which this translation belongs.
29 */
30 private LibraryTranslation libraryTranslation;
31
32 /***
33 * Gets the LibraryTranslation to which this Translation belongs.
34 *
35 * @return LibraryTranslation
36 */
37 protected LibraryTranslation getLibraryTranslation()
38 {
39 final String methodName = "Translation.getLibraryTranslation";
40
41
42 if (this.libraryTranslation == null)
43 {
44 throw new LibraryException(methodName + " - libraryTranslation can not be null");
45 }
46 return libraryTranslation;
47 }
48
49 /***
50 * Sets the LibraryTranslation to which this Translation belongs.
51 *
52 * @param translation the LibraryTranslation to which this Translation belongs.
53 */
54 protected void setLibraryTranslation(final LibraryTranslation translation)
55 {
56 libraryTranslation = translation;
57 }
58
59 /***
60 * Gets the fragment matching (using regular expressions) the specified name.
61 *
62 * @param name the name of the fragment to retrieve.
63 * @return Fragment
64 */
65 protected Fragment getFragment(final String name)
66 {
67 Fragment fragment = null;
68 Iterator names = fragments.keySet().iterator();
69
70
71
72 while (names.hasNext())
73 {
74 String nextName = (String)names.next();
75 if (name.matches(nextName))
76 {
77 fragment = (Fragment)fragments.get(nextName);
78 }
79 }
80
81
82
83 if (fragment == null && !this.isIgnorePattern(name))
84 {
85
86
87
88
89
90
91
92
93 }
94 return fragment;
95 }
96
97 /***
98 * Adds a new Translation fragment to the Translation.
99 *
100 * @param fragment
101 */
102 public void addFragment(final Fragment fragment)
103 {
104 ExceptionUtils.checkNull(
105 "fragment",
106 fragment);
107 fragment.setTranslation(this);
108 this.fragments.put(
109 fragment.getName(),
110 fragment);
111 }
112
113 /***
114 * Gets the name of this Translation.
115 *
116 * @return String
117 */
118 protected String getName()
119 {
120 return name;
121 }
122
123 /***
124 * @param name
125 */
126 protected void setName(final String name)
127 {
128 this.name = name;
129 }
130
131 /***
132 * Adds an <code>ignorePattern</code> to the Collection of ignorePatterns.
133 *
134 * @param ignorePattern the pattern to ignore.
135 */
136 public void addIgnorePattern(final String ignorePattern)
137 {
138 this.ignorePatterns.add(StringUtils.trimToEmpty(ignorePattern));
139 }
140
141 /***
142 * Adds an <code>validatePattern</code> to the Collection of validatePatterns.
143 *
144 * @param validatePattern the pattern to validate.
145 */
146 public void addValidatePattern(final String validatePattern)
147 {
148 this.validatePatterns.add(StringUtils.trimToEmpty(validatePattern));
149 }
150
151 /***
152 * Checks to see if the pattern is an ignore pattern. What this means is that if if this pattern matches on a
153 * regular expression found in the collection of ignore patterns then the TranslationLibrary won't complain if it
154 * doesn't match a fragment name.
155 *
156 * @param pattern
157 * @return boolean <code>true</code> if its an ignore pattern, <code>false</code> otherwise.
158 */
159 public boolean isIgnorePattern(String pattern)
160 {
161 boolean isIgnorePattern = false;
162 pattern = StringUtils.trimToEmpty(pattern);
163 Iterator ignorePatterns = this.ignorePatterns.iterator();
164
165
166
167 while (ignorePatterns.hasNext())
168 {
169 String nextIgnorePattern = StringUtils.trimToEmpty((String)ignorePatterns.next());
170 isIgnorePattern = pattern.matches(nextIgnorePattern);
171 if (isIgnorePattern)
172 {
173 break;
174 }
175 }
176 return isIgnorePattern;
177 }
178
179 /***
180 * Gets the "translated" value of this Fragment if it exists. That is, it retrieves the fragment body for the name
181 * of this fragment and replaces any fragment references with other fragment bodies (if they exist)
182 *
183 * @param name the name of the fragment.
184 * @param kind the kind of the fragment.
185 * @return String the translated body of the fragment kind.
186 */
187 protected String getTranslated(
188 String name,
189 String kind)
190 {
191
192 name = StringUtils.trimToEmpty(name);
193 kind = StringUtils.trimToEmpty(kind);
194
195 ExceptionUtils.checkEmpty(
196 "name",
197 name);
198
199 Fragment fragment = this.getFragment(name);
200 String translated = "";
201 if (fragment != null)
202 {
203 translated = fragment.getKind(kind);
204 String begin = "fragment{";
205 int beginLength = begin.length();
206 String end = "}";
207 for (int beginIndex = translated.indexOf(begin); beginIndex != -1;
208 beginIndex = translated.indexOf(begin))
209 {
210 String fragmentName = translated.substring(
211 beginIndex + beginLength,
212 translated.length());
213 int endIndex = fragmentName.indexOf(end);
214 if (endIndex != -1)
215 {
216 fragmentName = fragmentName.substring(
217 0,
218 endIndex);
219 }
220 StringBuffer toReplace = new StringBuffer(begin);
221 toReplace.append(fragmentName);
222 toReplace.append(end);
223 translated =
224 StringUtils.replace(
225 translated,
226 toReplace.toString(),
227 this.getTranslated(
228 fragmentName,
229 kind));
230 }
231 }
232 return TranslationUtils.removeExtraWhitespace(translated);
233 }
234
235 /***
236 * @see java.lang.Object#toString()
237 */
238 public String toString()
239 {
240 return ToStringBuilder.reflectionToString(this);
241 }
242 }