Upon first glance, looks good ;) Maybe you guys should roll it up into
core <hint> <hint>

Gili

Al Maw wrote:
> Igor Vaynberg wrote:
>> i guess it is not something that we support right now, but something
>> that is cleary needed. we need to build a resource that can load a css
>> file, parse for images, replace them, and then serve the altered content.
>>
>> i know almaw has been working on something like this but i dont know how
>> far he got. a patch would be welcome, if not then i guess you will have
>> to wait until one of the core devels has the time.
> 
> Sorry for the late reply - been on holiday. Please find attached
> something that might be useful.
> 
> You'll need to change CssResource#getResourceStream() to understand how
> to tell if your app is in debug mode or not (see discussion on the dev
> list a week or two ago about that).
> 
> Best regards,
> 
> Al Maw
> 
> 
> ------------------------------------------------------------------------
> 
> package foo.wicket.resources;
> 
> import wicket.Application;
> import wicket.AttributeModifier;
> import wicket.Component;
> import wicket.ResourceReference;
> import wicket.SharedResources;
> import wicket.markup.ComponentTag;
> import wicket.markup.html.WebMarkupContainer;
> import wicket.model.IModel;
> import wicket.model.Model;
> import wicket.util.value.ValueMap;
> 
> /**
>  * Created on 03-May-2006.
>  * @author Alastair Maw
>  */
> public class CssReference extends WebMarkupContainer {
>     
>     private static final long serialVersionUID = 1L;
> 
>     /**
>      * Construct.
>      * @param id component id
>      * @param referer the class that is refering; is used as the relative
>      * root for gettting the resource
>      * @param file reference as a string
>      */
>     public CssReference(final String id, final Class referer, final String 
> file) {
>         this(id, referer, new Model(file));
>     }
>     
>     public CssReference(final String id, final Class referer, final IModel 
> file) {
>         super(id);
>         IModel srcReplacement = new Model() {
>             private static final long serialVersionUID = 1L;
> 
>             public Object getObject(Component component) {
>                 
>                 Object o = file.getObject(component);
>                 if (o == null) {
>                     throw new IllegalArgumentException("The model must 
> provide a non-null object (component == " + component + ")");
>                 }
>                 if (!(o instanceof String)) {
>                     throw new IllegalArgumentException("The model must 
> provide an instance of String");
>                 }
>                 
>                 String f = 
> (String)component.getConverter().convert(file.getObject(component), 
> String.class);
>                 final SharedResources sharedResources = 
> Application.get().getSharedResources();
>                 CssResource resource = 
> (CssResource)sharedResources.get(referer, f, getLocale(), getStyle(), true);
>                 if (resource == null) {
>                     resource = new CssResource(getRequestCycle(), referer, 
> file.getObject(component).toString());
>                     sharedResources.add(referer, f, null, null, resource);
>                 }
> 
>                 String url = getRequestCycle().urlFor(new 
> ResourceReference(referer, f)).toString();
>                 return url;
> 
>             }
>         };
>         add(new AttributeModifier("href", true, srcReplacement));
>     }
> 
>     /**
>      * @see wicket.Component#onComponentTag(wicket.markup.ComponentTag)
>      */
>     protected void onComponentTag(ComponentTag tag) {
>         // Must be attached to a style tag
>         checkComponentTag(tag, "link");
>         ValueMap attributes = tag.getAttributes();
>         attributes.put("rel", "stylesheet");
>         attributes.put("type", "text/css");
>     }
> 
> }
> 
> 
> ------------------------------------------------------------------------
> 
> package foo.wicket.resources;
> 
> import java.io.BufferedReader;
> import java.io.IOException;
> import java.io.InputStreamReader;
> 
> import org.apache.commons.logging.Log;
> import org.apache.commons.logging.LogFactory;
> 
> import wicket.Application;
> import wicket.RequestCycle;
> import wicket.Resource;
> import wicket.ResourceReference;
> import wicket.WicketRuntimeException;
> import wicket.markup.html.PackageResourceReference;
> import wicket.markup.html.WebResource;
> import wicket.util.lang.Packages;
> import wicket.util.resource.IResourceStream;
> import wicket.util.resource.ResourceStreamNotFoundException;
> import wicket.util.resource.StringBufferResourceStream;
> import wicket.util.resource.locator.IResourceStreamLocator;
> import wicket.util.time.Time;
> 
> /**
>  * Created on 03-May-2006.
>  * @author Alastair Maw
>  */
> public class CssResource extends WebResource {
> 
>     private static final long serialVersionUID = 1L;
>     
>     private static Log log = LogFactory.getLog(CssResource.class);
>     
>     /** CSS definition */
>     private StringBufferResourceStream css = new StringBufferResourceStream();
> 
>     private Class scope;
>     private String path;
>     
>     public CssResource(RequestCycle cycle, Class scope, String path) {
>         this.scope = scope;
>         this.path = path;
>         refreshResource(cycle);
>     }
>     
>     private void refreshResource(RequestCycle cycle) {
>         String absolutePath = Packages.absolutePath(scope, path);
>         
>         // Locate the resource
>         IResourceStreamLocator locator = 
> Application.get().getResourceSettings().getResourceStreamLocator();
>         IResourceStream resourceStream = locator.locate(scope, absolutePath, 
> null, null, null);
> 
>         // Check that resource was found
>         if (resourceStream == null) {
>             throw new WicketRuntimeException("Unable to find package resource 
> [path = " + absolutePath + "]");
>         }
>         try {
>             try {
>                 css.clear();
>                 BufferedReader in = new BufferedReader(new 
> InputStreamReader(resourceStream.getInputStream()));
>                 
>                 int lastSlash = path.lastIndexOf('/');
>                 
>                 // We've requested a path/to/something/foo.css and now we 
> want to
>                 // strip off the foo.css from the end so we can construct 
> relative
>                 // links to url() resources, which we prefix things with.
>                 
>                 // Note that if we don't have a slash, we'll do a 
> substring(0, 0) == ""
>                 String prefix = path.substring(0, lastSlash + 1);
>                 
>                 // We assume that search and replace over the CSS is 
> expensive, CSS isn't that big,
>                 // and that memory is fairly cheap, so we make just throw it 
> all into a StringBuffer. 
>                 
>                 
>                 String line;
>                 while ((line = in.readLine()) != null) {
>                     
>                     // Check to see if we have a "url(" token.
>                     String[] tokens = line.split("url\\(", 2);
>                     if (tokens.length == 2) {
>                         
>                         // Create a new line with the bit before the "url(" 
> token and the token itself.
>                         String newLine = tokens[0] + "url(";
>                         
>                         // Find the matching closing bracket of the "url(" 
> token.
>                         tokens = tokens[1].split("\\)", 2);
>                         if (tokens.length == 2) {
>                             // Find the href for the included resource.
>                             String href = tokens[0];
>                             
>                             /*
>                              * The CSS 2 spec 
> (http://www.w3.org/TR/REC-CSS2/syndata.html#uri) says:
>                              * 
>                              * The format of a URI value is 'url(' followed 
> by optional whitespace
>                              * followed by an optional single quote (') or 
> double quote (") character
>                              * followed by the URI itself, followed by an 
> optional single quote (')
>                              * or double quote (") character followed by 
> optional whitespace followed
>                              * by ')'. The two quote characters must be the 
> same.
>                              */
>                             href = href.trim();
>                             if (href.length() > 0) {
>                                 if ((href.charAt(0) == '\'' && 
> href.charAt(href.length() - 1) == '\'') ||
>                                         href.charAt(0) == '"' && 
> href.charAt(href.length() - 1) == '"') {
>                                     href = href.substring(1, href.length() - 
> 1);
>                                 }
>                             }
>                             
>                             try {
>                                 String url;
>                                 
>                                 final String resolvedParents = 
> Packages.absolutePath("", prefix + href);
>                                 if (resolvedParents.startsWith("/")) {
>                                     url = cycle.urlFor(new 
> ResourceReference(resolvedParents.substring(1)) {
>                                         @Override
>                                         protected Resource newResource() {
>                                             return 
> ClassLoaderResource.get(resolvedParents);
>                                         }
>                                     }).toString();
>                                 }
>                                 else {
>                                     // Get a URL for packaged resource.
>                                     url = cycle.urlFor(new 
> PackageResourceReference(scope, resolvedParents)).toString();
>                                 }
>                                 
>                                 // Re-add the "url(" token's closing ")".
>                                 newLine += url;
>                                 newLine += ")";
>                                 newLine += tokens[1];
>                                 line = newLine;
>                             }
>                             catch (Exception e) {
>                                 log.info("Ignoring replacement for CSS 
> resource: " + href + " - ");
>                                 e.printStackTrace();
>                             }
>                         }
>                         
>                     }
>                     // Add the line to the output, with a newline.
>                     css.append(line);
>                     css.append("\n");
>                     css.setLastModified(Time.now());
>                 }
>             }
>             finally {
>                 resourceStream.close();
>             }
>         }
>         catch (ResourceStreamNotFoundException e) {
>             throw new WicketRuntimeException(e);
>         }
>         catch (IOException e) {
>             throw new WicketRuntimeException(e);
>         }
>     }
> 
>     // @see wicket.Resource#getResourceStream()
>     public IResourceStream getResourceStream() {
>         // We try to refresh resources on every load if we're in development 
> mode.
>         Application app = Application.get();
>         if (app instanceof MxWebApplication && 
>                 
> ((MxWebApplication)app).getAppMode().equals(Application.DEVELOPMENT)) {
>             RequestCycle cycle = RequestCycle.get();
>             // We need to check for null here, because Wicket gets the
>             // lastModified time without providing a RequestCycle threadlocal.
>             // We only refresh for the real requests.
>             if (cycle != null) {
>                 log.info("Reloading CSS resource " + path);
>                 refreshResource(cycle);
>             }
>             else {
>                 String absolutePath = Packages.absolutePath(scope, path);
>                 
>                 // Locate the resource
>                 IResourceStreamLocator locator = 
> Application.get().getResourceSettings().getResourceStreamLocator();
>                 IResourceStream resourceStream = locator.locate(scope, 
> absolutePath, null, null, null);
> 
>                 // Sort out the last modified time.
>                 css.setLastModified(resourceStream.lastModifiedTime());
>             }
>         }
>         return css;
>     }
> 
> }
> 
> 
> ------------------------------------------------------------------------
> 
> -------------------------------------------------------------------------
> Take Surveys. Earn Cash. Influence the Future of IT
> Join SourceForge.net's Techsay panel and you'll get the chance to share your
> opinions on IT & business topics through brief surveys -- and earn cash
> http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV
> 
> 
> ------------------------------------------------------------------------
> 
> _______________________________________________
> Wicket-user mailing list
> Wicket-user@lists.sourceforge.net
> https://lists.sourceforge.net/lists/listinfo/wicket-user

Attachment: signature.asc
Description: OpenPGP digital signature

-------------------------------------------------------------------------
Take Surveys. Earn Cash. Influence the Future of IT
Join SourceForge.net's Techsay panel and you'll get the chance to share your
opinions on IT & business topics through brief surveys -- and earn cash
http://www.techsay.com/default.php?page=join.php&p=sourceforge&CID=DEVDEV
_______________________________________________
Wicket-user mailing list
Wicket-user@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/wicket-user

Reply via email to