|
I'm doing common build implementation based on Ant 1.8 Ivy 2.2 and Nexus current status can be found hereBy default IBM Websphere Portal 6.0 uses the following chain to determine user locale Navigation State So when navigation state is lost there is a problem if we want to show content in a locale different from User Profile.
on this image if we change the language and click 'Certificate Managment' language will be taken from User profile not from current settings since navigation state will be lost. We can implement our own approach by writing a filter for wps.war which will use cookie with selected language. New Chain to determent User localeUser open portal browser default language is used . User selected different language-cookie is set with this language. New language is used. 1. Set cookie when a User selects languagewps.ear\wps.war\themes\html\theme\Default.jsp - page contains the language selection logic insert logic to set cookie when the user selects the language <script type="text/javascript"> dojo.addOnLoad(function(){ dojo.require("dojo.cookie"); dojo.query("a.change-language",dojo.byId("languagePart")).forEach(function(el){ dojo.connect(el,"onclick",function(_event){ _event.preventDefault(); _event.stopPropagation(); var loc=dojo.trim(el.innerHTML)==='ENG'?'en':'ru'; dojo.cookie("selectedUserLocale",loc,{path:"/"}); window.location=el.href; }); }); }); </script> ...... <a href='<portal-navigation:url command="ChangeLanguage" commandParam="en"/>' class='<%=styleAEn%> change-language'> ENG </a> ...... 2. Create Filter with Request WrapperLocaleRequestWrapperpublic class LocaleRequestWrapper extends HttpServletRequestWrapper implements IServletRequest { private String locale = null; private Locale localeObj; private List locales = new ArrayList(1); public LocaleRequestWrapper(HttpServletRequest request) { super(request); String selectedLocale = getLocaleFromCookie(request.getCookies()); String langCode = selectedLocale != null ? selectedLocale : request.getLocale().getLanguage(); if (langCode != null && langCode.trim().length() > 0) { this.locale = langCode; localeObj = new Locale(langCode); } if (locale != null) { locales.add(locale); } } private String getLocaleFromCookie(Cookie[] cookies) { if(cookies==null) return null; for (int i = 0; i < cookies.length; i++) { Cookie c=cookies[i]; if(!"selectedUserLocale".equals(c.getName())) continue; return c.getValue(); } return null; } public Object clone() throws CloneNotSupportedException { LocaleRequestWrapper crequest = (LocaleRequestWrapper) super.clone(); javax.servlet.ServletRequest inner = crequest.getRequest(); if (inner instanceof IServletRequest) crequest.setRequest((HttpServletRequest) ((IServletRequest) inner).clone()); else throw new CloneNotSupportedException(); return crequest; } public String getHeader(String key) { // get the original request HttpServletRequest request = (HttpServletRequest) getRequest(); // if the header request is for locale, return the stored locale if (!"Accept-Language".equalsIgnoreCase(key)) return request.getHeader(key); return locale != null ? locale : request.getHeader(key); } public Enumeration getHeaders(String key) { // get the original request HttpServletRequest request = (HttpServletRequest) getRequest(); // if the header request is for locale, return the stored locale if (!"Accept-Language".equalsIgnoreCase(key)) return request.getHeaders(key); return locale != null ? Collections.enumeration(locales) : request.getHeaders(key); } public Locale getLocale() { return localeObj != null ? localeObj:((HttpServletRequest)getRequest()).getLocale(); } public Enumeration getLocales() { return locale != null ? Collections.enumeration(locales) :((HttpServletRequest)getRequest()).getLocales(); } } LocaleServletFilterpublic class LocaleServletFilter implements Filter{ public void doFilter( ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { LocaleRequestWrapper wrapper = new LocaleRequestWrapper((HttpServletRequest)request); if (chain != null) chain.doFilter(wrapper, response); } public void destroy() { } public void init(FilterConfig arg0) throws ServletException { } } 3. Add filter mapping
<filter>
<filter-name>Locale Filter</filter-name>
<filter-class>...LocaleServletFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>Locale Filter</filter-name>
<url-pattern>/myportal/*</url-pattern>
</filter-mapping>
<filter-mapping>
<filter-name>Locale Filter</filter-name>
<url-pattern>/portal/*</url-pattern>
</filter-mapping>
4. Remove from Portal\wmm\wmmLDAPServerAttributes.xml preferredLanguage attributeMapto prevent portal looking the locale in the user profile Developing a multi-locale site using WebSphere Portal V5.1.0.1Idea has been taken from this article. The main idea is to restrict user to use only one session. For example if user logged in in one browser and then logged in in another one this restriction prevent users's work in the first browser. 1. DB schemaCREATE TABLE "DB2ADMIN"."LOGINUSERDATA" ( "CUSTOMERID" VARCHAR(100) NOT NULL , "SESSIONID" VARCHAR(300) NOT NULL , "NODEIP" VARGRAPHIC(100) NOT NULL , "TIMESTAMP" TIMESTAMP NOT NULL ) IN "USERSPACE1" ; ALTER TABLE "DB2ADMIN"."LOGINUSERDATA" ADD CONSTRAINT "CC1277458314344" PRIMARY KEY ("CUSTOMERID"); 2. Custom login moduleto be able to monitor user login data custom login module should be created LoginUserAuth.java public class LoginUserAuth extends com.ibm.wps.engine.commands.LoginUserAuth { private LoginUserService loginUserService= LoginUserService.INSTANCE; private static final Logger logger = Logger.getLogger(LoginUserAuth.class); protected void doPostLogin(RunData aRunData, String aUserID, String aPassword) throws WpsException { if(aUserID==null) return; loginUserService.saveUser(new LoginUserData(aUserID,aRunData.getSession().getId())); } } in WebSphere AS the following changes should be done in WP LoaderService Custom properties is added command.path with value com.minosiants.auth.cmd,com.ibm.wps.engine.commands, com.ibm.wps.dynamicui.commands 3. Portal filterTo be able to prevent usage of "old session" each request now should be checked if its session ls up to date. If it is not request should be redirected to logout page. UserSessionFilter.java public void doFilter(ServletRequest request, ServletResponse response , FilterChain chain) throws IOException, ServletException { HttpServletRequest req = (HttpServletRequest)request; HttpServletResponse resp = (HttpServletResponse)response; String userId=req.getRemoteUser(); if(userId==null){ chain.doFilter( request, response ); } if("wpsadmin".equals(userId)){ chain.doFilter( request, response ); return; } String logoutURL=generateLogoutURL(req,(HttpServletResponse)response); if(!loginUserService.isCurrientSession(userId, req.getRequestedSessionId())){ try { String url=ServletURLHelper.generateUrl("CUSTOM_LOGOUT", null, null, req, resp); request.setAttribute("logoutURL", logoutURL); if(!req.getRequestURI().toString().equals("/wps/portal")){ url=url.replaceAll("/wps/", "/"); filterConfig.getServletContext().getRequestDispatcher(url).forward(request, response); return; } } catch (StateException e) { e.printStackTrace(); } catch (NamingException e) { // TODO Auto-generated catch block e.printStackTrace(); } chain.doFilter( request, response ); return; } chain.doFilter( request, response ); } this filter should be added into wps.war web.xml web.xml .... <filter> <filter-name>UserSession</filter-name> <filter-class>com.minosiants.auth.filter.UserSessionFilter</filter-class> </filter> .... <filter-mapping> <filter-name>UserSession</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> .... 4. Custom logout portletTo make logout process more user friendly new portlet should be added. This portlet contains only view on jsp page. <script type="text/javascript"> dojo.addOnLoad(function(){ var myTimer = new dojox.timing.Timer(); myTimer.setInterval(1000); myTimer.onTick = function () { var sec=15; return function(){ sec=sec-1; dojo.byId("sec").innerHTML=sec; if(sec===0) window.location="/wps/portal"; }; }(); myTimer.start(); var b=dojo.byId("goButton"); dojo.connect(b, "onclick", function(event) { console.log("click"); event.preventDefault(); event.stopPropagation(); myTimer.stop(); window.location="/wps/portal"; }); }); </script> <script type="text/javascript"> dojo.addOnLoad(function(){ var myTimer = new dojox.timing.Timer(); myTimer.setInterval(1000); myTimer.onTick = function () { var sec=15; return function(){ sec=sec-1; dojo.byId("sec").innerHTML=sec; if(sec===0) window.location="/wps/portal"; }; }(); myTimer.start(); var b=dojo.byId("goButton"); dojo.connect(b, "onclick", function(event) { console.log("click"); event.preventDefault(); event.stopPropagation(); myTimer.stop(); window.location="/wps/portal"; }); }); </script> <script type="text/javascript"> dojo.addOnLoad(function(){ var myTimer = new dojox.timing.Timer(); myTimer.setInterval(1000); myTimer.onTick = function () { var sec=15; return function(){ sec=sec-1; dojo.byId("sec").innerHTML=sec; if(sec===0) window.location="/wps/portal"; }; }(); myTimer.start(); var b=dojo.byId("goButton"); dojo.connect(b, "onclick", function(event) { console.log("click"); event.preventDefault(); event.stopPropagation(); myTimer.stop(); window.location="/wps/portal"; }); }); </script> <div id="logoutInfo"> <h2><fmt:message key='logoutInfo'/></h2> <div id="pp"> <h2 id="hh"> <fmt:message key='beforeButton'/></h2> <button dojoType="dijit.form.Button" type="button" id="goButton" ><fmt:message key='goToLogin'/></button> </div> </div> source codelogin-module.zipjar should be created from this project and placed into \PortalServer\shared\app and websphera lib dir custom-logout-portlet.zipportlet for logout view Default approach used in IBM portlet application for integration resource bundles into view parts is really ugly. So I've created another taglib which contains one tag placeResourceBundleData OnePortletResource_en.propertiesfirstPage.my.title=placeResourceBundleData portal tag demo firstPage.message.hello=Hello firstPage.message.world=World index.jsp<%@taglib uri="http://minosiants.com/tl/core" prefix="pc"%> <head> <meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1" /> <title></title> <script src="http://o.aolcdn.com/dojo/1.4/dojo/dojo.xd.js" type="text/javascript"> </script> <script type="text/javascript"> dojo.addOnLoad(function(){ <pc:placeResourceBundleData bundle="com.minosiants.nl.OnePortletResource" /> var msg=ui.firstPage.message; dojo.byId("h1").innerHTML=msg.hello+" "+msg.world; }); </script> </head> <body> <h1>${ui.firstPage.my.title}</h1> <h1 id="h1"></h1> </body> </html> common-portal-taglib.zip - tag lib sourceI've created test web project to demonstrate how it works TestTaglib.zip
Web Anatomy MindMapAt Flickr
BusinessObjects ComponentsCRYSTAL REPORTS SERVER XI RELEASE 2 General ArchitectureThree components participate. BusinessObjects Portlets , Crystal Reports Server, InfoView BusinessObjects Web application - UI working with Crystal Reports Server. JAAS SSO and Ldap are used for the SSO. BusinessObjects Enterprise XI R2 PortalIntegration Kit Installation Guide for IBM WebSphere JAAS SSO Enablement Extensions Deployment Guide for IBM WebSphere Document List PortletThere were two problemsDescriptionDocument list contains list of the reports from crystal server. Each report is a link to InfoView which is responsible to open a report itself. When Document list opens - new portlet session is created and this session is alive unless any report is opened or portlet session timeout comes. It happens because InfoView also create a session. Both these session store session id a cookie JSESSIONID overwriting the previous value. Creation of any of these sessions assumes login into Crystal Report Server which means a new licence usage. With the restricted number of licences and active work at the portal and with the reports after a while we run out of the licences and unable to work further. SolutionSession cookie name of deployed InfoView should be changed from its default value DescriptionAccessing after a while of not using Document list portlet there is a some kind of timeout exception. SolutionRemove timeout of the session in the deployed document list ear Increase value of BusinessObjects Enterprise Token Timeout in deployed document list ear <context-param> Секреты мотивации персонала by @ForbesRussia via @splix интервью с Сергем Белоусовым
Интерестное описание создания программного продукта.
Labels: quote
30 predictions for the future of twitter Some interesting quotes to remember
Interesting in a restaurant|shop based on my location I'd be able to start talking and getting coupons. (this should be exposed later )
thats good
http://www.briansolis.com/2009/10/the-future-of-the-social-web/
it'd be nice to be in a colony of people with the same interest but in the same time I think it would narrow my view and bring the filling that nothing else exist . The most interesting thing would be at the intersection of different colonies . I't be nice to have a button "Go to completely different colony" LOL
It used to be blog where people store log of their life activity. Now it mostly social platform. Regarding to that almost everything is cyclic, probably mobile data would become Blog 3.0. Мтс предлагает тариф МТС Коннект c без лимитным интернетом
Проблема в том что стоимость исходящих вызовов на тарифе с безлимиитным интернетом 3 - 3,5 руб. звонки на обычный телефон по Питеру и Москве бесплатны, по России ~ 1 руб. Sipdroid настроил только вчера поэтому пока еще не знаю насколько стабильная эта штука , а voipcheap пользуюсь уже давно качество у них связи хорошее. Начал пользоваться HTC Hero и мое общее настроение - нравится. Первая не понятная вещь - наличие только английской локали (в российской версии доступны две локали русская и английская) мне казалось ,что телефон без физической клавиатуры и поэтому тут ограничений быть не должно Другая не очень удобная вещь это импорт контактов. Мне пришлось из старого телефона экспортировать контакты в gmail а от туда синхронизовать из на телефон. что совсем не удобно. Правда есть программа которая может импортировать их из vcard файлов прямо в hiro Import Contacts автор @bornmw. Последние заметки конечно такие устройства становятся очень удобными и полезными особенно с постоянным доступом в интернет. twidroid - крутая штука Надо еще настроить voip.
Labels: hero
Authors:
Book descriptionWelcome to the expanded second edition of Dan Cederholm's best-selling Web Standards Solutions. Web Standards are the standard technology specifications enforced by the World Wide Web Consortium (W3C) to make sure that web designers and browser manufacturers are using the same technology syntax. It is important that these implementations are the same throughout the Web, otherwise it becomes a messy proprietary place, and lacks consistency. These standards also allow content to be more compatible with multiple different viewing devices, such as screen readers for people with vision impairments, cell phones, PDFs, etc. HTML, XML, and CSS are all such technologies. This book is your essential guide to understanding the advantages you can bring to your web pages by implementing web standards and precisely how to apply them. Web standards such as XHTML and CSS are now fairly well-known technologies, and they will likely be familiar to you, the web designer. Indeed, they are all around you on the Web. However, within web standards still lies a challenge: while the browser's support for web standards is steadily increasing, many web developers and designers have yet to discover the real benefits of web standards and respect the need to adhere to them. The real art is in truly understanding the benefits and implementing the standards efficiently. As a simple example of its power, you can use CSS to lay out your pages instead of nesting tables. This can make file sizes smaller, allowing pages to load faster, ultimately increasing accessibility for all browsers, devices, and web users.
What you'll learnWeb Standards Solutions is broken down into 16 short chapters, each covering the theory and practice of different web standards concepts and showing multiple solutions to given problems for easy learning. You'll learn about multi-column layouts, using image replacement techniques to your best advantage, making the best use of tables and lists, and many more. This highly modular approach allows you to rapidly digest, understand, and utilize the essentials of web standards.
Who is this book for?Web developers and designers wanting to learn standards-based techniques to improve their sites ‚Äömaking them more efficient, more accessible, and transferrable across multiple browsers and devices. Information from book
|
|
I'm an IT Consultant working for Gemini-Systems. My main professional interests are Java EE and related technologies Russia, St. Petersburg
osgi links to resources
|
This is the home page for the Kaspar space.
Labels
Page: About Me
Page: AJAX
Page: ant
Page: Application Servers
Page: Books
Page: Bottom
Page: CSS
Page: Dynamic Languages
Page: JavaOne
Page: Maven
Page: MindMaps
Page: MySQL
Page: Notes
Page: Oracle
Page: Pipes
Page: PR of Gemini-Systems Spb
Page: REST
Page: shelfari
Page: Spring
Page: WebSphere Platform
Page: Социальное животное
Page: афон
Page: сельское хозяйство








Add Comment