I have created two issues for this. For the non-Web-MVC part: https://issues.apache.org/jira/browse/FREEMARKER-54 and the Web MVC part that builds on the first: https://issues.apache.org/jira/browse/FREEMARKER-55
Friday, June 2, 2017, 4:56:38 PM, Woonsan Ko wrote: > On Fri, Jun 2, 2017 at 5:05 AM, Daniel Dekany <[email protected]> wrote: >> Thursday, June 1, 2017, 5:09:07 PM, Woonsan Ko wrote: >> >>> On Wed, May 31, 2017 at 6:39 PM, Daniel Dekany <[email protected]> wrote: >>>> Wednesday, May 31, 2017, 6:09:32 PM, Woonsan Ko wrote: >>>> >>>>> On Tue, May 30, 2017 at 11:38 AM, Daniel Dekany <[email protected]> >>>>> wrote: >>>>>> Tuesday, May 30, 2017, 5:02:43 PM, Woonsan Ko wrote: >>>>> <snip> >>>>>>>>>> Speaking of which, soon there will be one. Anyone is interested in >>>>>>>>>> FM3 >>>>>>>>>> Spring integration? The goal is that FM3's builder-based >>>>>>>>>> configuration >>>>>>>>>> can be used seamlessly for creating the Spring beans. So certainly a >>>>>>>>>> freemarker-spring module need to be added, which extends some classes >>>>>>>>>> to implement FactoryBean interface and such. Also some configuration >>>>>>>>>> defaults, like the TemplateLoader need to be different for sure, and >>>>>>>>>> we need a TemplateLoader that uses Spring's Resource API. (I will >>>>>>>>>> create an issue for it after I have polished the configuration API a >>>>>>>>>> bit more.) >>>>>>>>> >>>>>>>>> Yes, I am interested in FM3 spring integration. >>>>>>>>> One question is, are we going to replace spring framework's default >>>>>>>>> freemarker view support [1] by freemarker-spring in FM3? >>>>>>>> >>>>>>>> That would be the idea. And that will be the only possibility at the >>>>>>>> beginning, as they only have FM2 support (and I guess contributing to >>>>>>>> ASF/FM makes more sense than contributing to them). >>>>>>> >>>>>>> OK, got it. >>>>>>> >>>>>>>> >>>>>>>>> Anyway, I'll happily help with this as soon as you create an issue. >>>>>>>> >>>>>>>> Great! That will happen in a few days. >>>>>>> >>>>>>> I will try to list features of spring framework support for >>>>>>> compatibility and other possible new features and improvements first. >>>>>>> And, I'll try to discuss those items here soon. >>>>>> >>>>>> Sounds good. >>>>> >>>>> I've reviewed spring online documentation and tried to list all the >>>>> features currently supported. We'll probably need to provide >>>>> compatible solutions or alternatives for FM3. I added some notes on >>>>> some items, too. Prioritization wasn't considered yet. >>>>> >>>>> ----- >>>>> >>>>> 1. Configuration support >>>>> >>>>> 1.1. Generic Configuration Factory bean support (that can be used for >>>>> non web-apps) >>>>> - FreeMarkerConfigurationFactoryBean >>>>> - Note: perhaps the builder should be used internally inside the >>>>> factory bean? >>>> >>>> The FactoryBean should extend Configuration.ExtenableBuilder. So it's >>>> not even some internal stuff; ExtenableBuilder is public and was added >>>> for things like this. >>>> >>>>> 1.2. Web MVC Configurer bean support >>>>> - FreeMarkerConfigurer >>>> >>>> Ah that... whole thing. It's really confusing. It starts there that >>>> it's hard to grasp for the user what a FreeMarkerConfigurer really is. >>>> Because, we already have Configuration, and even a Spring-specific >>>> class, FreeMarkerConfigurationFactoryBean that creates that. To >>>> configure FreeMarker you need a Configuration, so a Configuration is >>>> the real "FreeMarker configurer". But the "FreeMarkerConfigurer" name >>>> suggests the same ("I configure FreeMarker"). So how is it different? >>>> To make it more confusing, it's basically >>>> FreeMarkerConfigurationFactoryBean (which is just a Configuration >>>> Builder) with a few quirks: >>>> >>>> - It's technically not a FactoryBean. So instead of relying on Spring IoC >>>> injection as usual, the dependent bean (FreeMarkerViewResolver >>>> usually) has to call getConfiguration() on it. >>>> >>>> - getConfiguration() might returns a Configuration that wasn't built by >>>> the FreeMarkerConfigurer! If you call setConfiguration(Configuration), >>>> then that Configuration will be returned, and things you set on >>>> FreeMarkerConfigurer (which is a Configuration Builder) doesn't >>>> mater. Anyway, you would (or just I would?) think that if you want >>>> the Web View stuff to use a specific Configuration, then you just inject >>>> that Configuration bean into FreeMarkerViewResolver. But no, because >>>> FreeMarkerViewResolver needs a FreeMarkerConfigurer. In fact, >>>> FreeMarkerViewResolver doesn't need that directly. Instead, it just >>>> specifies a class, FreeMarkerView, which in turn "manually" looks up >>>> the FreeMarkerConfigurer bean with BeanFactoryUtils. >>>> >>>> - It provides a TaglibFactory object as well. I have to give that to >>>> it, as that's at least something that Configuration doesn't do. But >>>> if that will be the only obstacle of getting rid of >>>> FreeMarkerConfigurer, then we stuff that into the Configuration, >>>> like as a custom attribute (custom setting, if I have renamed it as >>>> discussed), and as a real JavaBean property in our ExtenableBuilder >>>> subclass. >>>> >>>> BTW Velocity support have the same hard to follow logic. Maybe it's >>>> necessary, I don't know. Still, I wonder if we can make it more >>>> elegant and less confusing for users. (Is it nicer with Thymeleaf for >>>> example?) What I'm hoping for is that we can just use a Configuration >>>> bean instead, and FreeMarkerView looks that up. The tricky part is how >>>> to differentiate that bean from the other Configuration beans. The >>>> natural solution is using a "web" qualifier, which is easy to follow >>>> for the user as well (no magic, it's obvious how it works). But some >>>> may feel it's not very stream lined (because I believe we can't >>>> transparently make a bean qualified, so the user has to add it to its >>>> configuration). So another possibility is subclassing Configuration, >>>> so then we first look for a WebConfiguration (and then of course we >>>> will also need a FreeMarkerWebConfigurationFactoryBean - note the >>>> "Web" in it), and only if that's not found we look for "web" qualified >>>> Configuration. But maybe all this is too different from Spring >>>> tradition... I'm just thinking aloud. >>> >>> I will look into it further. But in general, the current >>> FreeMarkerConfigurer based configuration looks confusing to me, and as >>> you pointed out it's not even a FactoryBean and it's found out by the >>> view resolver, etc. I feel like it could be neater. Let me investigate >>> other things further and come back. >>> >>>> >>>> BTW, I believe e-mail generation and other miscellaneous FreeMarker >>>> applications (report generation, etc.) will be at least as important >>>> as web pages nowadays. >>> >>> +1 >>> >>>> >>>>> and FreeMarkerViewResolver (basically extending UrlBasedViewResolver) >>>>> - Note: the view resolver finds out the configurer bean by type by >>>>> default. >>>> >>>> Well, if we stick to the approach with FreeMarkerConfigurer and all >>>> that, the it's good enough. Otherwise see above. >>>> >>>>> Seems good enough for normal web application to me. Same >>>>> pattern in the configurer by using builder internally? >>>> >>>> (The builders aren't meant to be internal, but it's the same as >>>> earlier.) >>>> >>>>> 1.3. Annotation / XML Schema based configuration support >>>>> (FreeMarkerConfigurer type bean) >>>>> - Note: ViewResolverRegistry#freemarker() finds a bean by exact type >>>>> of FreeMarkerConfigurer. alternative? >>>> >>>> What can we do about this at all? I mean, we can't add methods to this >>>> class. >>> >>> Yeah. We may lose @EnableWebMvc feature since it seems tightly coupled >>> with FreeMarkerConfigurer. Indeed, ViewResolverRegistry is created in >>> a hard-coded way directly by WebMvcConfigurationSupport. >> >> Yet again, it might worth checking out what the Thymeleaf guys did, as >> they focus heavily on Spring integration. > > OK. That sounds right. I'll take a look at how they do. > >> >>>> >>>>> (ref: >>>>> http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#mvc-config-view-resolvers) >>>>> >>>>> 1.4. XML Schema based configuration support >>>>> - Note: alternative for this? >>>>> <mvc:view-resolvers> >>>>> <!-- SNIP --> >>>>> <mvc:freemarker cache="false"/> >>>>> </mvc:view-resolvers> >>>> >>>> XML config is low priority, I guess. >>> >>> +1 >>> >>>> >>>>> 2. View Resolution support >>>>> - FreeMarkerViewResolver and FreeMarkerView >>>>> >>>>> 3. Tempplating Support >>>>> >>>>> 3.1. JSP Tag Libraries support >>>>> - Spring / Spring form tag libraries and Spring binding macro support. >>>>> - Note: It looks like spring macros (spring.ftl) are duplicate >>>>> effort to the JSTL tag libraries, so I'm wondering if the macros were >>>>> originally introduced before freemarker JSTL tag library support >>>>> wasn't there or wasn't good enough. If so, perhaps can we stick to >>>>> using JSTL tag libraries directly without having to rewrite/provide >>>>> the macros? >>>>> Or would it bring huge disruption in spring-mvc/freemarker community? >>>>> Need to validate it more... >>>> >>>> So I guess that's where my domain knowledge ends. Which JSTL tags are >>>> these? The Spring macros I have seen in SO questions and such call >>>> Spring-specific functionality, not JSTL... or I just don't know what >>>> JSTL can do. (Basic JSTL tags/functions are often duplicates core >>>> FreeMarker functionality, like c:if, c:forEach, etc.) BTW, many JSTL >>>> tags actually don't work with FreeMarker JSP support (I remember we >>>> have a test case on @Ignore which demonstrates that). Pretty much only >>>> traditional custom JSP tags do. >>> >>> I'm sorry for my confusion. I should have used (spring custom) "JSP >>> tags", not "JSTL tags". >>> >>> Examples of "duplicate efforts" to me: >>> - In Spring JSP Taglibs >>> (https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-tld.html), >>> it has 'message' tag. >>> In spring.ftl, it also has 'message' macro and variants >>> ('messageArgs', 'messageArgsText', ...). >>> Perhaps there is a little to help with the macros, but developers >>> can use jsp tag lib in ftl directly. >>> - In Spring Form Taglibs >>> (https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-form-tld.html), >>> it has 'checkboxes' tag. >>> spring.ftl defines macros too for the same functionality. >>> >>> So, I'm thinking if we can stick with JSP taglibs only, then we might >>> not need to support those macros separately. >> >> I hope (but haven't checked) that Spring has a >> view-technology-independent layer of this, and then the JSP custom >> tags (and FreeMarker macros) are just adapting that to the conventions > > Ah, yes. That's something to check. Good point. > >> of the view technology (JSP, FTL). My concern with simply solving it >> with yet another adapter layer (FTL to JSP) is that the logic of at >> least some of these JSP tags is foreign from (modern) FTL. And the >> same certainly goes for other view technologies as well (here again >> it's might be a good idea to look what they did at Thymeleaf). > > OK. > >> >> Let's take spring:message for example. Why's this a tag at all? It's >> function, or even just a hash. If I had to expose such functionality >> to FTL-s, it would look like `${messages.hello}` and >> `${messages.hello(userName)}` and `${messages.hello(arg1, arg2, >> argN)}`. This also means that you can pass a resolved message as an >> argument to another macro/function: `<@foo messages.hello(userName)>`. >> And what's up with the escaping parameters? Because normally HTML >> autoescaping is ideally on, users has to do nothing to escape, and >> they can write ${messages.thisIsAlreadyHTML?noEsc} otherwise. We >> leverage core FTL functionality here, not need for any extra >> `messages` parameter for that. (Not to mention that in general it's >> not good that the user who inserts the message has to know if it's >> already HTML or not. I mean they can't decide it there, because it's >> already either HTML or plain text in the message data source. So, >> `messages` should know that (the data source should store that >> meta-information somehow). Then, `message.foo` returns an FTL String >> if `foo` is plain text, and FTL HTML markup-output if `foo` is HTML >> message, hence there's no need for ?noEsc in the last case, as >> FreeMarker knows that it needs no further escaping. >> >> In the future we might run into other cases where we can't utilize FTL >> features because the JSP obviously doesn't do that, and hence they >> have duplicated it, or just don't have it. >> >> There are also cases of the opposite of it, i.e., where JSP can do >> something that we can't, or at least it ugly and not idiomatic. Take >> for example the `var` and `scope` attributes of the spring:messages >> tag. Well, FTL has no out-parameters, nor scopes (even if the >> FreemarkerServlet data-model emulates the last to an extent). But if >> we solve this functionality with a function, as we should anyway (see >> above), we return that thing, so we don't need an out-param. If >> instead we just call spring:message with the JSP custom tag support of >> FreeMarker, it won't magically transform it to a function. > > Good point! Sound better with extra ftl macros, not depending only on JSP > tags. > >> >>>>> 3.2. HTML escaping and XHTML compliance?? >>>>> - ref: >>>>> http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#views-form-macros-html-escaping, >>>>> >>>>> https://docs.spring.io/spring/docs/current/spring-framework-reference/html/spring-form-tld.html >>>>> >>>>> - Note: If we stick with JSTL tags without any extra macros (3.1), I >>>>> guess we won't need this special variable settings for escaping any >>>>> more.. >>>> >>>> So this is about how Spring (or you are saying, JSTL?) generated HTML >>>> fragments use escaping internally. >>> >>> Sorry again, I should have said 'spring jsp tag libraries' instead. >>> For example, the 'message' tag already has 'htmlEscape' attribute. So, >>> when using the tag, ftl can use that attribute directly. >>> By the way, 'htmlEscape' spring jsp tag wouldn't be used in .ftl, >>> practically speaking as FM provides a better support. >> >> Yip. >> >>>>> 4. Testing support >>>>> - ref: >>>>> http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#spring-mvc-test-server-htmlunit >>>>> - Note: Make sure it works... >>>>> >>>>> 5. Micellaneous >>>>> >>>>> 5.1. Sending E-Mail support >>>>> - ref: >>>>> http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#mail-templates-example >>>>> - Note: might be a low-hanging fruit by giving an example with >>>>> freemarker instead... >>>> >>>> Yeah... especially if they will ever switch to freaking post-2.3.23 >>>> FreeMarker (they don't upgrade since we are incubating...), because >>>> auto-escaping is missing from that example, and 2.3.24 does it much >>>> better than 2.3.23. >>>> >>>>> ----- >>>>> >>>>> Personally, I wish to have the following in the future too: >>>>> >>>>> 6. More wishes >>>>> >>>>> 6.1. Generic FreeMarker Configuration Factory with JSTL support >>>>> - I have an HMVC web application framework which uses spring >>>>> framework as IoC, not MVC and Freemarker as view templating, but it >>>>> needs to support JSTL tag libraries. So far I have dispatched requests >>>>> to Freemarker servlet. I wish to configure a configuration factory and >>>>> use the service somehow directly without having to use request >>>>> dispatching any more... >>>> >>>> Not sure I follow, but isn't this using JSP support without >>>> FreemarkerServlet? It's not well documented, but possible, like Spring >>>> MVC does that too. >>> >>> Oh yeah? >> >> I'm not entirely sure... It think so as FreeMarkerConfigurer stores a >> TaglibFactory. > > Yeah, I think I took a glance at that. Will look into it further. > > After studying how Thymeleaf guys do further, I can probably share better > ideas. > > Regards, > > Woonsan > >> >>> That's good then. I'll try it later. >> >>> Thanks for all your input! I'll look into more detail and discuss further >>> later. >>> >>> Cheers, >>> >>> Woonsan >>> >>>> >>>>> ----- >>>>> >>>>> Folks, if you have experienced with spring + freemarker, please >>>>> review/correct my understandings and chime in here. >>>>> Also, it is probably a good time to speak up if you wish to have in >>>>> the future. ;-) >>>>> >>>>>> >>>>>> I was a bit boggled down with the configuration API polishing, so I >>>>>> haven't yet made the Jira issue. But I belive there's enough things to >>>>>> do with the Spring integration before that becomes a problem. Things >>>>>> will keep changing under it anyway. But that's just how refactoring >>>>>> goes, and the same will happen again and again with freemarker-dom and >>>>>> freemarker-servlet too. >>>>> >>>>> Yes, I think this spring framework support could be started in >>>>> separate feature branch(es). >>>>> I guess the most important ones from the list above are 1.1, 1.2, 2, and >>>>> 3.1. >>>>> Perhaps I can start working for those 4 items first in my github >>>>> branch to merge it later. >>>>> If there are other people who want to contribute to any of those, we >>>>> can consider a shared feature branch instead... >>>>> >>>>>> >>>>>> The goal would be not using the setSetting(String, String) API when >>>>>> configuring under Spring, and work with beans and bean properties >>>>>> cleanly. Ideally, only the builder classes need to be subclassed to >>>>>> add some Spring annotations/interfaces and Spring-specific defaults. >>>>> >>>>> I see. And I saw your builder class is really extensible. That's great! >>>>> >>>>>> >>>>>> One thing that I will surely want to do in FM3 is allowing mixed >>>>>> positional and named parameters in templates, like `f(1, 2, foo=3, >>>>>> bar=4)` or `<@m 1, 2 foo=3 bar=4/>`. That's probably good to know when >>>>>> it comes to calling Spring features from templates. (Of course this >>>>>> will require replacing TemplateMethodModel and TemplateDirectiveModel >>>>>> etc. with something better. Cleaning up the mess around the callable >>>>>> objects is part of FM3 anyway.) >>>>> >>>>> Sounds good. I haven't found a good example of 'calling Spring >>>>> features from templates' yet though. Maybe I'm missing something >>>>> important... >>>>> >>>>> Regards, >>>>> >>>>> Woonsan >>>>> >>>>>> >>>>>>> Regards, >>>>>>> >>>>>>> Woonsan >>>>>>> >>>>>>>> >>>>>>>>> Regards, >>>>>>>>> >>>>>>>>> Woonsan >>>>>>>>> >>>>>>>>> [1] >>>>>>>>> https://docs.spring.io/spring/docs/current/spring-framework-reference/html/view.html#view-velocity-contextconfig >>>>>>>>> >>>>>>>>>> >>>>>>>>>>> Best regards, >>>>>>>>>>> >>>>>>>>>>> Michael Brohl >>>>>>>>>>> ecomify GmbH >>>>>>>>>>> www.ecomify.de >>>>>>>>>>> >>>>>>>>>>> >>>>>>>>>>> Am 17.05.17 um 14:29 schrieb Daniel Dekany: >>>>>>>>>>>> Wednesday, May 17, 2017, 2:26:29 AM, Taher Alkhateeb wrote: >>>>>>>>>>>> >>>>>>>>>>>>> Yeah I closed it because it was a proposal for a PoC which you >>>>>>>>>>>>> pretty much >>>>>>>>>>>>> got done while I slacked :) Should I re-open? If yes then perhaps >>>>>>>>>>>>> it should >>>>>>>>>>>>> be renamed by removing the "PoC" part? >>>>>>>>>>>> No, then it was right to close it after all. You can create an >>>>>>>>>>>> issue >>>>>>>>>>>> for resolving the TODO-s and polishing the stuff it you think, >>>>>>>>>>>> though >>>>>>>>>>>> honestly FM3 has tons and tons of non-Jiraed things to do... What >>>>>>>>>>>> really counts if someone is interested in actually working on them. >>>>>>>>>>>> (I'm not saying this to point at you or anyone. It's unpaid work >>>>>>>>>>>> etc., >>>>>>>>>>>> and if the project can't attract contributors, it's the fault of >>>>>>>>>>>> the >>>>>>>>>>>> project and of its key persons, like me. The aspect that concerns >>>>>>>>>>>> me >>>>>>>>>>>> is that if I do all the technical stuff, even if I was some kind of >>>>>>>>>>>> superhuman one man army (and BTW I'm not) who can grind through >>>>>>>>>>>> everything in time regardless, that will be a serious problem when >>>>>>>>>>>> it >>>>>>>>>>>> comes to Apache incubation voting...) >>>>>>>>>>>> >>>>>>>>>>>> >>>>>>>>>>>>> On Tue, May 16, 2017 at 11:10 PM, Daniel Dekany >>>>>>>>>>>>> <[email protected]> wrote: >>>>>>>>>>>>> >>>>>>>>>>>>>> I saw the Jira issue for migrating to Gradle was closed, but to >>>>>>>>>>>>>> be >>>>>>>>>>>>>> clear it's far from done. Like, a major TODO is building the >>>>>>>>>>>>>> release >>>>>>>>>>>>>> artifacts; the root project should do that (or should that be yet >>>>>>>>>>>>>> another sub-project instead?). >>>>>>>>>>>>>> >>>>>>>>>>>>>> The second most important deficiency is producing all the 3 Maven >>>>>>>>>>>>>> artifacts for each published module (the usual artifact plus src >>>>>>>>>>>>>> and >>>>>>>>>>>>>> javadoc). Currently we only produce one artifact per module, and >>>>>>>>>>>>>> it's >>>>>>>>>>>>>> not even signed. >>>>>>>>>>>>>> >>>>>>>>>>>>>> BTW, I have factored out Manual generation into freemarker-manual >>>>>>>>>>>>>> (non-published module). There's also a TODO there as its build >>>>>>>>>>>>>> doesn't >>>>>>>>>>>>>> produce anything yet. >>>>>>>>>>>>>> >>>>>>>>>>>>>> -- >>>>>>>>>>>>>> Thanks, >>>>>>>>>>>>>> Daniel Dekany >>>>>>>>>>> >>>>>>>>>>> >>>>>>>>>> >>>>>>>>>> -- >>>>>>>>>> Thanks, >>>>>>>>>> Daniel Dekany >>>>>>>>>> >>>>>>>>> >>>>>>>> >>>>>>>> -- >>>>>>>> Thanks, >>>>>>>> Daniel Dekany >>>>>>>> >>>>>>> >>>>>> >>>>>> -- >>>>>> Thanks, >>>>>> Daniel Dekany >>>>>> >>>>> >>>> >>>> -- >>>> Thanks, >>>> Daniel Dekany >>>> >>> >> >> -- >> Thanks, >> Daniel Dekany >> > -- Thanks, Daniel Dekany
