1 package org.paneris.bibliomania;
2
3 import java.io.BufferedWriter;
4 import java.io.ByteArrayInputStream;
5 import java.io.File;
6 import java.io.FileInputStream;
7 import java.io.FileWriter;
8 import java.io.IOException;
9 import java.io.InputStream;
10 import java.io.Writer;
11 import java.util.Enumeration;
12 import java.util.Hashtable;
13
14 import org.melati.Melati;
15 import org.melati.admin.AdminSpecialised;
16 import org.melati.poem.CachedSelection;
17 import org.melati.poem.Capability;
18 import org.melati.poem.PoemThread;
19 import org.melati.poem.Table;
20 import org.melati.template.MarkupLanguage;
21 import org.melati.poem.util.ArrayUtils;
22 import org.melati.poem.util.EmptyEnumeration;
23 import org.melati.poem.Treeable;
24 import org.paneris.bibliomania.fti.FTIException;
25 import org.paneris.bibliomania.fti.Text;
26 import org.paneris.bibliomania.generated.BookBase;
27
28 public class Book extends BookBase implements AdminSpecialised, Text {
29
30 public String getFulltitle() {
31 String it = getFulltitleifdifferent();
32 return it == null ? getTitle() : it;
33 }
34
35 public File getSourceDir() {
36 return new File(getBibliomaniaDatabase().getContentRootDir(), getPath());
37 }
38
39 public class TooManyBooksException extends SequenceFTILimitsException {
40
41
42
43 private static final long serialVersionUID = 1L;
44
45 public TooManyBooksException(int seq, int limit) {
46 super(seq, limit);
47 }
48
49 public Table getTable() {
50 return getBookTable();
51 }
52
53 public String getParentTable() {
54 return "author";
55 }
56 }
57
58 public void setAuthorsequence(Integer s) {
59 if (s != null && s.intValue() >= Chapter.ftiTextID_book_limit)
60 throw new TooManyBooksException(
61 s.intValue(),
62 Chapter.ftiTextID_book_limit);
63 super.setAuthorsequence(s);
64 }
65
66 private void notifyChangedTextIDs() {
67 for (Enumeration c = getChapters(); c.hasMoreElements();)
68 ((Chapter)c.nextElement()).notifyChangedTextID();
69 }
70
71 public void setAuthor(Author author) {
72 if (!author.troid().equals(this.author)) {
73 super.setAuthor(author);
74 setAuthorsequence(author.firstFreeAuthorsequence());
75 notifyChangedTextIDs();
76 }
77 }
78
79 private CachedSelection<Chapter> chapters = null;
80
81 public Enumeration getChapters() {
82 if (getTroid() == null)
83 return new EmptyEnumeration<Chapter>();
84 else {
85 if (chapters == null)
86 chapters =
87 getBibliomaniaDatabase()
88 .getChapterTable()
89 .getBookColumn()
90 .cachedSelectionWhereEq(getTroid());
91 return chapters.objects();
92 }
93 }
94
95 public Enumeration getProductAssociations() {
96 return getProductAssociations(
97 getBibliomaniaDatabaseTables()
98 .getProductAssociationTable()
99 .getBookColumn());
100 }
101
102 public Enumeration getMembersSlowly() {
103 return getChapters();
104 }
105
106 public Chapter chapter(int sequence) {
107 getChapters();
108 return (Chapter)chapters.nth(sequence);
109 }
110
111 public Chapter getChapter0() {
112 getChapters();
113 return (Chapter)chapters.firstObject();
114 }
115
116 public String getCha0JS() {
117 Boolean hnfp = getHasnofrontpage();
118 if (hnfp != null && hnfp.booleanValue()) {
119 Chapter c0 = getChapter0();
120 if (c0 != null)
121 return c0.troid().toString();
122 }
123
124 return "null";
125 }
126
127 public void setSection(Section section) {
128 if (!(section == null
129 ? this.section == null
130 : section.troid().equals(this.section))) {
131 super.setSection(section);
132 notifyChangedTextIDs();
133 }
134 }
135
136 public Capability getCanReadContent() {
137 Capability it = getOverridecanreadcontent();
138 return it == null ? getSection().getDefaultcanreadcontent() : it;
139 }
140
141 public String adminHandle(Melati melati, MarkupLanguage markupLanguage)
142 throws Exception {
143 return null;
144 }
145
146 public String adminSpecialFacilities(
147 Melati melati,
148 MarkupLanguage markupLanguage)
149 throws Exception {
150 return getBibliomaniaDatabase().getWMTemplet("Book-specials");
151 }
152
153 public long ftiTextID() {
154 return ftiTextID_start() | ((1L << Chapter.ftiTextID_book_shift) - 1);
155 }
156
157 public InputStream body() throws IOException {
158 if (Boolean.TRUE.equals(getHasnofrontpage()))
159 return new ByteArrayInputStream((getTitle() +
160
161 " xyxyx xyxyx").getBytes());
162 else {
163 File f = getFrontPageFile();
164 if (f.exists()) {
165 InputStream it = new FileInputStream(f);
166 PoemThread.toTidy().add(it);
167 return it;
168 } else
169 return new ByteArrayInputStream(new byte[0]);
170 }
171 }
172
173 public InputStream bodyForFragment() throws IOException {
174 return body();
175 }
176
177 public long ftiTextID_start() {
178 return Chapter.ftiTextID(
179 getSectionTroid().intValue(),
180 getAuthorTroid().intValue(),
181 getAuthorsequence().intValue(),
182 0);
183 }
184
185 public long ftiTextID_limit() {
186 return ftiTextID_start() + (1L << Chapter.ftiTextID_book_shift);
187 }
188
189 public Unit getParentUnit() {
190 return getAuthor();
191 }
192
193 public String getDisplayName() {
194 return getFulltitle();
195 }
196
197 public void appendCacheSubpath(StringBuffer buffer) {
198 getAuthor().appendCacheSubpath(buffer);
199 buffer.append('/');
200 buffer.append(troid());
201 }
202
203 public void readKeyDotTxt() {
204 org.paneris.bibliomania.population.KeyDotTxtFilter.populate(this);
205 }
206
207 public static final String frontPageFileName = "index.html";
208 public static final String frontPageSourceFileName = "index.wm";
209
210 protected Hashtable<String, Boolean> speciallyTreatedInCache() {
211 Hashtable<String, Boolean> them = new Hashtable<String, Boolean>();
212 for (Enumeration c = getChapters(); c.hasMoreElements();)
213 them.put(((Chapter)c.nextElement()).getFilename(), Boolean.TRUE);
214 them.put(frontPageSourceFileName, Boolean.TRUE);
215 them.put(frontPageFileName, Boolean.TRUE);
216 return them;
217 }
218
219 public File getFrontPageFile() {
220 return new File(getCachePath(), "index.html");
221 }
222
223 public boolean hasTOC() {
224 File toc = new File(getSourceDir(), "index.wm");
225 return toc.exists();
226 }
227 public void index() throws IOException {
228 try {
229 getBibliomaniaDatabase().infoFTI().index(this);
230 } catch (IOException e) {
231 throw e;
232 } catch (Exception e) {
233 throw new FTIException(e);
234 }
235 }
236
237 public void encache() throws Exception {
238 super.encache();
239 File whole = new File(getCachePath(), "whole.html");
240
241 {
242 Writer w = new BufferedWriter(new FileWriter(whole));
243 try {
244 getBibliomaniaDatabase().interpolateTemplateToFile("Whole.wm", whole, this);
245 } finally {
246 try {
247 w.close();
248 } catch (Exception e) {
249 }
250 }
251 }
252
253 Boolean hnfp = getHasnofrontpage();
254 if (hnfp != null && !hnfp.booleanValue()) {
255 getBibliomaniaDatabase().interpolateTemplateToFile(
256 "read/Book.wm",
257 getFrontPageFile(),
258 this);
259 }
260 }
261
262 public SectionGroup getReadArea() {
263 return getSection().getReadArea();
264 }
265
266
267
268
269 public Treeable[] children = null;
270
271 @SuppressWarnings({ "rawtypes", "unchecked" })
272 public Treeable[] getChildren() {
273 if (children == null) {
274 Object[] kids = ArrayUtils.arrayOf((Enumeration<Object>)getChapters());
275 children = new Treeable[kids.length];
276 for (int i=0; i<kids.length; i++) {
277 children[i] = (Treeable)kids[i];
278 }
279 }
280 return children;
281 }
282
283
284
285 public String getName() {
286 return getDisplayName();
287 }
288 }