Any chance you could provide this as a patch? I believe this would be a nice feature to have in Roller's core.
Thanks, Matt On Thu, Nov 19, 2009 at 6:43 AM, <[email protected]> wrote: > Hello, > > Remembered a while back someone asked if it was possible to reload a theme > rather than restarting the container for development purposes. > > Rather than upgrading my laptop I decided to see if it was possible. > Roller needs a few mods, but seems to work, also does not seem to be much > of an overhead either. > > > Add a method to theme manager > > /** > * This is a development only method which reloads theme data from > themes > * stored on the filesystem in the webapp /themes/ directory. > * > * @param reloadTheme > * the reload theme > * > * @return true, if theme was reloaded from disk > */ > public boolean reLoadThemeFromDisk(String reloadTheme); > > > also impl: > > /** > * @see ThemeManager#reLoadThemeFromDisk(String) > */ > public boolean reLoadThemeFromDisk(String reloadTheme) { > > boolean reloaded = false; > > try { > > Theme theme = new SharedThemeFromDir(this.themeDir > + File.separator > + reloadTheme); > > if (theme != null) { > > Theme loadedTheme = (Theme) > themes.get(theme.getId()); > > if (loadedTheme != null > && theme.getLastModified() > .after(loadedTheme.getLastModified())) { > themes.remove(theme.getId()); > themes.put(theme.getId(), theme); > reloaded = true; > } > > } > > } catch (Throwable unexpected) { > log.error("Problem reloading theme " + > reloadTheme, unexpected); > } > > return reloaded; > > } > > Modify SharedThemeFromDir to update the last modified in SharedTheme: see > **** Set Last Modified ***** > > /** > * Load all the elements of this theme from disk and cache them. > */ > private void loadThemeFromDisk() throws > ThemeInitializationException { > > log.debug("Parsing theme descriptor for " + > this.themeDir); > > ThemeMetadata themeMetadata = null; > try { > // lookup theme descriptor and parse it > ThemeMetadataParser parser = new > ThemeMetadataParser(); > InputStream is = new FileInputStream(this.themeDir > + File.separator > + "theme.xml"); > themeMetadata = parser.unmarshall(is); > } catch (Exception ex) { > throw new ThemeInitializationException( > "Unable to parse theme descriptor > for theme " > + this.themeDir, > ex); > } > > log.debug("Loading Theme " + themeMetadata.getName()); > > // use parsed theme descriptor to load Theme data > setId(themeMetadata.getId()); > setName(themeMetadata.getName()); > setDescription(themeMetadata.getName()); > setAuthor(themeMetadata.getAuthor()); > **** Set Last Modified ***** > // setLastModified(new Date()); > setEnabled(true); > > // load resource representing preview image > File previewFile = new File(this.themeDir + File.separator > + themeMetadata.getPreviewImage()); > if (!previewFile.exists() || !previewFile.canRead()) { > log.warn("Couldn't read theme [" + this.getName() > + "] preview image file [" > + themeMetadata.getPreviewImage() > + "]"); > } else { > this.previewImage = new > SharedThemeResourceFromDir(themeMetadata > .getPreviewImage(), previewFile); > } > > // load stylesheet if possible > if (themeMetadata.getStylesheet() != null) { > > ThemeMetadataTemplate stylesheetTmpl = > themeMetadata > .getStylesheet(); > > // construct File object from path > File templateFile = new File(this.themeDir + > File.separator > + > stylesheetTmpl.getContentsFile()); > > // read stylesheet contents > String contents = loadTemplateFile(templateFile); > if (contents == null) { > // if we don't have any contents then skip > this one > log.error("Couldn't load stylesheet theme > [" + this.getName() > + "] template file [" + > templateFile + "]"); > } else { > > // construct ThemeTemplate representing > this file > SharedThemeTemplate theme_template = new > SharedThemeTemplate( > this, > themeMetadata.getId() + ":" > + > stylesheetTmpl.getName(), > WebsiteTemplate.ACTION_CUSTOM, > stylesheetTmpl.getName(), > stylesheetTmpl > .getDescription(), contents, stylesheetTmpl > .getLink(), new Date(templateFile > .lastModified()), stylesheetTmpl > .getTemplateLanguage(), false, false); > > // store it > this.stylesheet = theme_template; > > // add it to templates list > addTemplate(theme_template); > } > > // **** Set Last Modified ***** > setLastModified(new > Date(templateFile.lastModified())); > } > > // go through static resources and add them to the theme > String resourcePath = null; > Iterator resourcesIter = > themeMetadata.getResources().iterator(); > while (resourcesIter.hasNext()) { > resourcePath = (String) resourcesIter.next(); > > // construct ThemeResource object from resource > File resourceFile = new File(this.themeDir + > File.separator > + resourcePath); > > // Continue reading theme even if problem > encountered with one file > if (!resourceFile.exists() || > !resourceFile.canRead()) { > log.warn("Couldn't read theme [" + > this.getName() > + "] resource file [" + > resourcePath + "]"); > continue; > } > > // add it to the theme > setResource(resourcePath, new > SharedThemeResourceFromDir( > resourcePath, resourceFile)); > > // **** Set Last Modified ***** > Date lstModified = new > Date(resourceFile.lastModified()); > if (getLastModified() == null > || > lstModified.after(getLastModified())) { > setLastModified(lstModified); > } > } > > // go through templates and read in contents to a > ThemeTemplate > ThemeTemplate theme_template = null; > ThemeMetadataTemplate templateMetadata = null; > Iterator templatesIter = > themeMetadata.getTemplates().iterator(); > while (templatesIter.hasNext()) { > templateMetadata = (ThemeMetadataTemplate) > templatesIter.next(); > > // construct File object from path > File templateFile = new File(this.themeDir + > File.separator > + > templateMetadata.getContentsFile()); > > String contents = loadTemplateFile(templateFile); > if (contents == null) { > // if we don't have any contents then skip > this one > throw new > ThemeInitializationException("Couldn't load theme [" > + this.getName() + "] > template file [" + templateFile > + "]"); > } > > // construct ThemeTemplate representing this file > theme_template = new SharedThemeTemplate(this, > themeMetadata > .getId() > + ":" + > templateMetadata.getName(), templateMetadata > .getAction(), > templateMetadata.getName(), templateMetadata > .getDescription(), contents, > templateMetadata.getLink(), > new > Date(templateFile.lastModified()), templateMetadata > .getTemplateLanguage(), > templateMetadata.isHidden(), > templateMetadata.isNavbar()); > > // add it to the theme > addTemplate(theme_template); > > // **** Set Last Modified ***** > Date lstModified = new > Date(templateFile.lastModified()); > if (getLastModified() == null > || > lstModified.after(getLastModified())) { > setLastModified(lstModified); > } > } > } > > > Then in PageServlet reload the theme and then clear the caches > > // generate cache key > String cacheKey = null; > if (isSiteWide) { > cacheKey = siteWideCache.generateKey(pageRequest); > } else { > cacheKey = weblogPageCache.generateKey(pageRequest); > } > > // **** Development only. Reload if theme has been modified *** > if > (WebloggerConfig.getBooleanProperty("site.themeReloadMode")) { > try { > > ThemeManager manager = null; > manager = > WebloggerFactory.getWeblogger().getThemeManager(); > > boolean reloaded = > manager.reLoadThemeFromDisk(website.getEditorTheme()); > > if (reloaded) { > > if (isSiteWide) { > siteWideCache.clear(); > } else { > websitePageCache.clear(); > } > } > > } catch (Exception e1) { > // ignored > } > > } > > // cached content checking > if ((!this.excludeOwnerPages || !pageRequest.isLoggedIn()) && > request.getAttribute("skipCache") == null) { > > > Cheers Greg > > > > > Share our environment commitment - conserve resources and contribute to the > reduction of CO2 emissions by not printing the email unless absolutely > necessary to do so. > > Any opinions expressed are those of the author, not Ricoh UK Ltd. This > communication does not constitute either offer or acceptance of any > contractually binding agreement. Such offer or acceptance must be > communicated in writing. It is the responsibility of the recipient to ensure > this email and attachments are free from computer viruses before use and the > sender accepts no responsibility or liability for any such computer viruses. > > Ricoh UK Ltd. may monitor the content of emails sent and received via its > network for the purpose of ensuring compliance with its policies and > procedures. This communication contains information, which may be > confidential or privileged. The information is intended solely for the use of > the individual or entity named above. If you are not the intended recipient, > be aware that any disclosure, copying, distribution or use of the contents of > this information is prohibited. If you have received this communication in > error, please notify the sender immediately by return email with a copy to > [email protected] . Please contact us on +44 (0) 208 261 4000 if you > need assistance. > > Registered in England No: 473236 > VAT No: GB524161280
