You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@velocity.apache.org by "Jarkko Viinamäki (JIRA)" <de...@velocity.apache.org> on 2009/12/23 11:29:29 UTC

[jira] Updated: (VELOCITY-742) Easily Add/Remove/Replace Directives Without Cracking Open Velocity Jar

     [ https://issues.apache.org/jira/browse/VELOCITY-742?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]

Jarkko Viinamäki updated VELOCITY-742:
--------------------------------------

    Attachment: velocity-742.patch

OK. This patch now provides two new public methods in VelocityEngine and Velocity classes:

removeDirective(String name)
loadDirective(String className)

Note that all parser instances use the same set of directives so it's not possible to disable e.g. #include directive for certain page rendering but still keep it active for other possibly concurrent page renderings. Note also that you need to first call init on Velocity or VelocityEngine before you start removing directives (otherwise the autoinit "overwrites" the removal operation). See the Velocity742TestCase.

Note! After applying the patch, you need to run "ant parser test" in order to update the generated Parser.java and other related classes.

--

I also noticed that there was a hidden bug in the code: RuntimeInstance keeps a map of directives in variable called runtimeDirectives. When a new parser was created that variable was passed to the Parser but the parser made a HashMap copy of the runtimeDirectives (this was one of the speed improvements since it slows things down if many parsers hammer the same synchronized map).

Therefore when addDirective, removeDirective etc. were called in RuntimeInstance, they had no effect since all the created parsers still had a copy of the old runtimeDirectives map.

I fixed it so that Parser instances do not have a copy of the directives map at all. Instead, they redirect e.g. getDirective and isDirective calls to RuntimeInstance which uses unsynchronized HashMap for the lookups. When the runtimeDirectives map is modified (new directive is added or an old one is deleted), a new HashMap is created as a copy and the reference is updated so that subsequent calls to RuntimeInstance.getDirective use the newly created map (Copy-on-Write pattern I guess).

Nathan & others, please take a look at this when you have time and check if I did something really silly.

Merry Christmas! :)

> Easily Add/Remove/Replace Directives Without Cracking Open Velocity Jar
> -----------------------------------------------------------------------
>
>                 Key: VELOCITY-742
>                 URL: https://issues.apache.org/jira/browse/VELOCITY-742
>             Project: Velocity
>          Issue Type: New Feature
>          Components: Engine
>    Affects Versions: 1.6.2
>            Reporter: Tim White
>            Priority: Minor
>         Attachments: velocity-742.patch
>
>
> There are two use cases that I have for this issue:
> 1) We need to turn off #include in order to parse .html files that include SSI directives:  <!--#include virtual=""-->  (we always use #parse in our world, so no loss for #include going away)
> 2) We need to supply our own version of #parse that contains the development hooks that I described in a different issue.
> Right now, the only crisp way to do is is to crack open the velocity .jar and make these changes, which is very risky, because future developers may upgrade to new versions of Velocity and not realize that there are customizations and/or not understand how to remake them....not to mention in a shared-classpath environment, we don't always have control over which copy of the Velocity .jar we're using.
> Ideally, there would be config options like this:
> directive_remove ("#parse", "#include")
> directive_add ("#parse", "com.qwest.velocity.directives.Parse")
> Thanks!
> Tim

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.


---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@velocity.apache.org
For additional commands, e-mail: dev-help@velocity.apache.org