001    /**
002     * Copyright (c) 2000-2011 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.setup;
016    
017    import com.liferay.portal.NoSuchUserException;
018    import com.liferay.portal.dao.jdbc.util.DataSourceSwapper;
019    import com.liferay.portal.events.StartupAction;
020    import com.liferay.portal.kernel.cache.CacheRegistryUtil;
021    import com.liferay.portal.kernel.cache.MultiVMPoolUtil;
022    import com.liferay.portal.kernel.dao.jdbc.DataAccess;
023    import com.liferay.portal.kernel.dao.jdbc.DataSourceFactoryUtil;
024    import com.liferay.portal.kernel.deploy.hot.HotDeployUtil;
025    import com.liferay.portal.kernel.language.LanguageUtil;
026    import com.liferay.portal.kernel.log.Log;
027    import com.liferay.portal.kernel.log.LogFactoryUtil;
028    import com.liferay.portal.kernel.util.CalendarFactoryUtil;
029    import com.liferay.portal.kernel.util.CentralizedThreadLocal;
030    import com.liferay.portal.kernel.util.FileUtil;
031    import com.liferay.portal.kernel.util.ListUtil;
032    import com.liferay.portal.kernel.util.LocaleUtil;
033    import com.liferay.portal.kernel.util.ParamUtil;
034    import com.liferay.portal.kernel.util.PortalLifecycleUtil;
035    import com.liferay.portal.kernel.util.PropertiesParamUtil;
036    import com.liferay.portal.kernel.util.PropertiesUtil;
037    import com.liferay.portal.kernel.util.PropsKeys;
038    import com.liferay.portal.kernel.util.StringPool;
039    import com.liferay.portal.kernel.util.UnicodeProperties;
040    import com.liferay.portal.kernel.util.Validator;
041    import com.liferay.portal.kernel.webcache.WebCachePoolUtil;
042    import com.liferay.portal.model.Account;
043    import com.liferay.portal.model.Company;
044    import com.liferay.portal.model.Contact;
045    import com.liferay.portal.model.User;
046    import com.liferay.portal.security.auth.FullNameGenerator;
047    import com.liferay.portal.security.auth.FullNameGeneratorFactory;
048    import com.liferay.portal.security.auth.ScreenNameGenerator;
049    import com.liferay.portal.security.auth.ScreenNameGeneratorFactory;
050    import com.liferay.portal.service.AccountLocalServiceUtil;
051    import com.liferay.portal.service.CompanyLocalServiceUtil;
052    import com.liferay.portal.service.QuartzLocalServiceUtil;
053    import com.liferay.portal.service.ServiceContext;
054    import com.liferay.portal.service.UserLocalServiceUtil;
055    import com.liferay.portal.theme.ThemeDisplay;
056    import com.liferay.portal.util.PortalInstances;
057    import com.liferay.portal.util.PortalUtil;
058    import com.liferay.portal.util.PropsValues;
059    import com.liferay.portal.util.WebKeys;
060    
061    import java.io.IOException;
062    
063    import java.sql.Connection;
064    
065    import java.util.Calendar;
066    import java.util.List;
067    import java.util.Locale;
068    import java.util.Properties;
069    
070    import javax.servlet.http.HttpServletRequest;
071    import javax.servlet.http.HttpServletResponse;
072    import javax.servlet.http.HttpSession;
073    
074    import javax.sql.DataSource;
075    
076    import org.apache.struts.Globals;
077    
078    /**
079     * @author Manuel de la Peña
080     * @author Julio Camarero
081     * @author Brian Wing Shun Chan
082     */
083    public class SetupWizardUtil {
084    
085            public static final String PROPERTIES_FILE_NAME =
086                    "portal-setup-wizard.properties";
087    
088            public static boolean isDefaultDatabase(HttpServletRequest request) {
089                    boolean hsqldb = ParamUtil.getBoolean(
090                            request, "defaultDatabase",
091                            PropsValues.JDBC_DEFAULT_URL.contains("hsqldb"));
092    
093                    boolean jndi = Validator.isNotNull(PropsValues.JDBC_DEFAULT_JNDI_NAME);
094    
095                    return hsqldb && !jndi;
096            }
097    
098            public static boolean isSetupFinished() {
099                    if (PropsValues.SETUP_WIZARD_ENABLED) {
100                            return _setupFinished;
101                    }
102    
103                    return true;
104            }
105    
106            public static void setSetupFinished(boolean setupFinished) {
107                    _setupFinished = setupFinished;
108            }
109    
110            public static void testDatabase(HttpServletRequest request)
111                    throws Exception {
112    
113                    String driverClassName = _getParameter(
114                            request, PropsKeys.JDBC_DEFAULT_DRIVER_CLASS_NAME,
115                            PropsValues.JDBC_DEFAULT_DRIVER_CLASS_NAME);
116                    String url = _getParameter(request, PropsKeys.JDBC_DEFAULT_URL, null);
117                    String userName = _getParameter(
118                            request, PropsKeys.JDBC_DEFAULT_USERNAME, null);
119                    String password = _getParameter(
120                            request, PropsKeys.JDBC_DEFAULT_PASSWORD, null);
121    
122                    _testConnection(driverClassName, url, userName, password);
123            }
124    
125            public static void updateLanguage(
126                    HttpServletRequest request, HttpServletResponse response) {
127    
128                    String languageId = _getParameter(
129                            request, PropsKeys.COMPANY_DEFAULT_LOCALE,
130                            PropsValues.COMPANY_DEFAULT_LOCALE);
131    
132                    Locale locale = LocaleUtil.fromLanguageId(languageId);
133    
134                    List<Locale> availableLocales = ListUtil.fromArray(
135                            LanguageUtil.getAvailableLocales());
136    
137                    if (!availableLocales.contains(locale)) {
138                            return;
139                    }
140    
141                    PropsValues.COMPANY_DEFAULT_LOCALE = languageId;
142    
143                    HttpSession session = request.getSession();
144    
145                    session.setAttribute(Globals.LOCALE_KEY, locale);
146                    session.setAttribute(WebKeys.SETUP_WIZARD_DEFAULT_LOCALE, languageId);
147    
148                    LanguageUtil.updateCookie(request, response, locale);
149    
150                    ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
151                            WebKeys.THEME_DISPLAY);
152    
153                    themeDisplay.setLanguageId(languageId);
154                    themeDisplay.setLocale(locale);
155            }
156    
157            public static void updateSetup(
158                            HttpServletRequest request, HttpServletResponse response)
159                    throws Exception {
160    
161                    UnicodeProperties unicodeProperties =
162                            PropertiesParamUtil.getProperties(request, _PROPERTIES_PREFIX);
163    
164                    boolean databaseConfigured = _isDatabaseConfigured(unicodeProperties);
165    
166                    _processAdminProperties(request, unicodeProperties);
167                    _processDatabaseProperties(
168                            request, unicodeProperties, databaseConfigured);
169    
170                    updateLanguage(request, response);
171    
172                    unicodeProperties.put(
173                            PropsKeys.SETUP_WIZARD_ENABLED, String.valueOf(false));
174    
175                    HttpSession session = request.getSession();
176    
177                    session.setAttribute(
178                            WebKeys.SETUP_WIZARD_PROPERTIES, unicodeProperties);
179    
180                    boolean propertiesFileUpdated = _writePropertiesFile(unicodeProperties);
181    
182                    session.setAttribute(
183                            WebKeys.SETUP_WIZARD_PROPERTIES_UPDATED, propertiesFileUpdated);
184    
185                    if (!databaseConfigured) {
186                            _reloadServletContext(request, unicodeProperties);
187                    }
188    
189                    _updateCompany();
190                    _updateAdminUser(request);
191    
192                    _initPlugins();
193            }
194    
195            private static String _getParameter(
196                    HttpServletRequest request, String name, String defaultValue) {
197    
198                    name = _PROPERTIES_PREFIX.concat(name).concat(StringPool.DOUBLE_DASH);
199    
200                    return ParamUtil.getString(request, name, defaultValue);
201            }
202    
203            /**
204             * @see {@link com.liferay.portal.servlet.MainServlet#initPlugins}
205             */
206            private static void _initPlugins() {
207                    HotDeployUtil.setCapturePrematureEvents(false);
208    
209                    PortalLifecycleUtil.flushInits();
210            }
211    
212            private static boolean _isDatabaseConfigured(
213                    UnicodeProperties unicodeProperties) {
214    
215                    String defaultDriverClassName = unicodeProperties.get(
216                            PropsKeys.JDBC_DEFAULT_DRIVER_CLASS_NAME);
217                    String defaultPassword = unicodeProperties.get(
218                            PropsKeys.JDBC_DEFAULT_PASSWORD);
219                    String defaultURL = unicodeProperties.get(PropsKeys.JDBC_DEFAULT_URL);
220                    String defaultUsername = unicodeProperties.get(
221                            PropsKeys.JDBC_DEFAULT_USERNAME);
222    
223                    if (PropsValues.JDBC_DEFAULT_DRIVER_CLASS_NAME.equals(
224                                    defaultDriverClassName) &&
225                            PropsValues.JDBC_DEFAULT_PASSWORD.equals(defaultPassword) &&
226                            PropsValues.JDBC_DEFAULT_URL.equals(defaultURL) &&
227                            PropsValues.JDBC_DEFAULT_USERNAME.equals(defaultUsername) ) {
228    
229                            return true;
230                    }
231    
232                    return false;
233            }
234    
235            private static void _processAdminProperties(
236                            HttpServletRequest request, UnicodeProperties unicodeProperties)
237                    throws Exception {
238    
239                    String companyName = _getParameter(
240                            request, PropsKeys.COMPANY_DEFAULT_NAME, "Liferay");
241    
242                    PropsValues.COMPANY_DEFAULT_NAME = companyName;
243    
244                    FullNameGenerator fullNameGenerator =
245                            FullNameGeneratorFactory.getInstance();
246    
247                    String firstName = _getParameter(
248                            request, PropsKeys.DEFAULT_ADMIN_FIRST_NAME, "Test");
249    
250                    PropsValues.DEFAULT_ADMIN_FIRST_NAME = firstName;
251    
252                    String lastName = _getParameter(
253                            request, PropsKeys.DEFAULT_ADMIN_LAST_NAME, "Test");
254    
255                    PropsValues.DEFAULT_ADMIN_LAST_NAME = lastName;
256    
257                    String fullName = fullNameGenerator.getFullName(
258                            firstName, null, lastName);
259    
260                    PropsValues.ADMIN_EMAIL_FROM_NAME = fullName;
261    
262                    unicodeProperties.put(PropsKeys.ADMIN_EMAIL_FROM_NAME, fullName);
263    
264                    String emailAddress = _getParameter(
265                            request, PropsKeys.ADMIN_EMAIL_FROM_ADDRESS, "test@liferay.com");
266    
267                    PropsValues.ADMIN_EMAIL_FROM_ADDRESS = emailAddress;
268                    PropsValues.DEFAULT_ADMIN_EMAIL_ADDRESS = emailAddress;
269    
270                    unicodeProperties.put(
271                            PropsKeys.DEFAULT_ADMIN_EMAIL_ADDRESS, emailAddress);
272    
273                    ScreenNameGenerator screenNameGenerator =
274                            ScreenNameGeneratorFactory.getInstance();
275    
276                    String screenName = null;
277    
278                    try {
279                            screenName = screenNameGenerator.generate(0, 0, emailAddress);
280                    }
281                    catch (Exception e) {
282                            screenName = "test";
283                    }
284    
285                    PropsValues.DEFAULT_ADMIN_SCREEN_NAME = screenName;
286    
287                    unicodeProperties.put(PropsKeys.DEFAULT_ADMIN_SCREEN_NAME, screenName);
288            }
289    
290            private static void _processDatabaseProperties(
291                            HttpServletRequest request, UnicodeProperties unicodeProperties,
292                            boolean databaseConfigured)
293                    throws Exception {
294    
295                    boolean defaultDatabase = ParamUtil.getBoolean(
296                            request, "defaultDatabase", true);
297    
298                    if (defaultDatabase || databaseConfigured) {
299                            unicodeProperties.remove(PropsKeys.JDBC_DEFAULT_URL);
300                            unicodeProperties.remove(PropsKeys.JDBC_DEFAULT_DRIVER_CLASS_NAME);
301                            unicodeProperties.remove(PropsKeys.JDBC_DEFAULT_USERNAME);
302                            unicodeProperties.remove(PropsKeys.JDBC_DEFAULT_PASSWORD);
303                    }
304            }
305    
306            private static void _reloadServletContext(
307                            HttpServletRequest request, UnicodeProperties unicodeProperties)
308                    throws Exception {
309    
310                    // Data sources
311    
312                    Properties jdbcProperties = new Properties();
313    
314                    jdbcProperties.putAll(unicodeProperties);
315    
316                    jdbcProperties = PropertiesUtil.getProperties(
317                            jdbcProperties,"jdbc.default.",true);
318    
319                    DataSourceSwapper.swapCounterDataSource(jdbcProperties);
320                    DataSourceSwapper.swapLiferayDataSource(jdbcProperties);
321    
322                    // Caches
323    
324                    CacheRegistryUtil.clear();
325                    MultiVMPoolUtil.clear();
326                    WebCachePoolUtil.clear();
327                    CentralizedThreadLocal.clearShortLivedThreadLocals();
328    
329                    // Quartz
330    
331                    QuartzLocalServiceUtil.checkQuartzTables();
332    
333                    // Startup
334    
335                    StartupAction startupAction = new StartupAction();
336    
337                    startupAction.run(null);
338    
339                    // Servlet context
340    
341                    HttpSession session = request.getSession();
342    
343                    PortalInstances.reload(session.getServletContext());
344            }
345    
346            private static void _testConnection(
347                            String driverClassName, String url, String userName,
348                            String password)
349                    throws Exception {
350    
351                    Class.forName(driverClassName);
352    
353                    Connection connection = null;
354    
355                    try {
356                            DataSource dataSource = DataSourceFactoryUtil.initDataSource(
357                                    driverClassName, url, userName, password);
358    
359                            connection = dataSource.getConnection();
360                    }
361                    finally {
362                            DataAccess.cleanUp(connection);
363                    }
364            }
365    
366            private static void _updateAdminUser(HttpServletRequest request)
367                    throws Exception {
368    
369                    // Email address
370    
371                    ThemeDisplay themeDisplay = (ThemeDisplay)request.getAttribute(
372                            WebKeys.THEME_DISPLAY);
373    
374                    User user = null;
375    
376                    try {
377                            user = UserLocalServiceUtil.getUserByEmailAddress(
378                                    PortalUtil.getDefaultCompanyId(),
379                                    PropsValues.ADMIN_EMAIL_FROM_ADDRESS);
380                    }
381                    catch (NoSuchUserException nsue) {
382                            user = UserLocalServiceUtil.getUserByEmailAddress(
383                                    PortalUtil.getDefaultCompanyId(), "test@liferay.com");
384    
385                            user = UserLocalServiceUtil.updateEmailAddress(
386                                    user.getUserId(), StringPool.BLANK,
387                                    PropsValues.ADMIN_EMAIL_FROM_ADDRESS,
388                                    PropsValues.ADMIN_EMAIL_FROM_ADDRESS);
389                    }
390    
391                    // First and last name
392    
393                    String greeting = LanguageUtil.format(
394                            themeDisplay.getLocale(), "welcome-x",
395                            " " + PropsValues.ADMIN_EMAIL_FROM_NAME, false);
396    
397                    Contact contact = user.getContact();
398    
399                    Calendar birthdayCal = CalendarFactoryUtil.getCalendar();
400    
401                    birthdayCal.setTime(contact.getBirthday());
402    
403                    int birthdayMonth = birthdayCal.get(Calendar.MONTH);
404                    int birthdayDay = birthdayCal.get(Calendar.DAY_OF_MONTH);
405                    int birthdayYear = birthdayCal.get(Calendar.YEAR);
406    
407                    user = UserLocalServiceUtil.updateUser(
408                            user.getUserId(), StringPool.BLANK, StringPool.BLANK,
409                            StringPool.BLANK, false, user.getReminderQueryQuestion(),
410                            user.getReminderQueryAnswer(), user.getScreenName(),
411                            user.getEmailAddress(), user.getFacebookId(), user.getOpenId(),
412                            user.getLanguageId(), user.getTimeZoneId(), greeting,
413                            user.getComments(), PropsValues.DEFAULT_ADMIN_FIRST_NAME,
414                            user.getMiddleName(), PropsValues.DEFAULT_ADMIN_LAST_NAME,
415                            contact.getPrefixId(), contact.getSuffixId(), contact.isMale(),
416                            birthdayMonth, birthdayDay, birthdayYear, contact.getSmsSn(),
417                            contact.getAimSn(), contact.getFacebookSn(), contact.getIcqSn(),
418                            contact.getJabberSn(), contact.getMsnSn(), contact.getMySpaceSn(),
419                            contact.getSkypeSn(), contact.getTwitterSn(), contact.getYmSn(),
420                            contact.getJobTitle(), null, null, null, null, null,
421                            new ServiceContext());
422    
423                    // Password
424    
425                    user = UserLocalServiceUtil.updatePasswordReset(user.getUserId(), true);
426    
427                    HttpSession session = request.getSession();
428    
429                    session.setAttribute(WebKeys.SETUP_WIZARD_PASSWORD_UPDATED, true);
430            }
431    
432            private static void _updateCompany() throws Exception {
433                    Company company = CompanyLocalServiceUtil.getCompanyById(
434                            PortalInstances.getDefaultCompanyId());
435    
436                    Account account = company.getAccount();
437    
438                    String name = account.getName();
439    
440                    if (!name.equals(PropsValues.COMPANY_DEFAULT_NAME)) {
441                            account.setName(PropsValues.COMPANY_DEFAULT_NAME);
442    
443                            AccountLocalServiceUtil.updateAccount(account);
444                    }
445            }
446    
447            private static boolean _writePropertiesFile(
448                    UnicodeProperties unicodeProperties) {
449    
450                    try {
451                            FileUtil.write(
452                                    PropsValues.LIFERAY_HOME, PROPERTIES_FILE_NAME,
453                                    unicodeProperties.toString());
454    
455                            return true;
456                    }
457                    catch (IOException ioe) {
458                            _log.error(ioe, ioe);
459    
460                            return false;
461                    }
462            }
463    
464            private final static String _PROPERTIES_PREFIX = "properties--";
465    
466            private static Log _log = LogFactoryUtil.getLog(SetupWizardUtil.class);
467    
468            private static boolean _setupFinished = false;
469    
470    }