<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"><html xmlns="http://www.w3.org/1999/xhtml" lang="en"><head><meta http-equiv="Content-Type" content="text/html;charset=UTF-8"/><link rel="stylesheet" href="../jacoco-resources/report.css" type="text/css"/><link rel="shortcut icon" href="../jacoco-resources/report.gif" type="image/gif"/><title>LocalizationService.java</title><link rel="stylesheet" href="../jacoco-resources/prettify.css" type="text/css"/><script type="text/javascript" src="../jacoco-resources/prettify.js"></script></head><body onload="window['PR_TAB_WIDTH']=4;prettyPrint()"><div class="breadcrumb" id="breadcrumb"><span class="info"><a href="../jacoco-sessions.html" class="el_session">Sessions</a></span><a href="../index.html" class="el_report">Fulcrum Localization</a> &gt; <a href="index.source.html" class="el_package">org.apache.fulcrum.localization</a> &gt; <span class="el_source">LocalizationService.java</span></div><h1>LocalizationService.java</h1><pre class="source lang-java linenums">package org.apache.fulcrum.localization;


/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * &quot;License&quot;); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * &quot;AS IS&quot; BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */


import java.util.Locale;
import java.util.ResourceBundle;

import javax.servlet.http.HttpServletRequest;

/**
 * &lt;p&gt;
 * Provides localization functionality using the interface provided
 * by &lt;code&gt;ResourceBundle&lt;/code&gt;, plus leverages a &quot;search path&quot;
 * style traversal of the &lt;code&gt;ResourceBundle&lt;/code&gt; objects named by
 * the &lt;code&gt;locale.default.bundles&lt;/code&gt; to discover a value for a
 * given key.
 * &lt;/p&gt;
 *
 * &lt;p&gt;
 * It is suggested that one handle
 * &lt;a href=&quot;http://www.math.fu-berlin.de/~rene/www/java/tutorial/i18n/message/messageFormat.html&quot;&gt;dealing with concatenated messages&lt;/a&gt;
 * using &lt;code&gt;MessageFormat&lt;/code&gt; and properties files.
 * &lt;/p&gt;
 *
 * @author &lt;a href=&quot;mailto:jon@latchkey.com&quot;&gt;Jon S. Stevens&lt;/a&gt;
 * @author &lt;a href=&quot;mailto:dlr@finemaltcoding.com&quot;&gt;Daniel Rall&lt;/a&gt;
 * @author &lt;a href=&quot;mailto:leonardr@collab.net&quot;&gt;Leonard Richardson&lt;/a&gt;
 * @author &lt;a href=&quot;mailto:mcconnell@apache.org&quot;&gt;Stephen McConnell&lt;/a&gt;
 * @author &lt;a href=&quot;mailto:tv@apache.org&quot;&gt;Thomas Vandahl&lt;/a&gt;
 * @version $Id$
 */
public interface LocalizationService extends SimpleLocalizationService
{
<span class="fc" id="L53">    String ROLE = LocalizationService.class.getName();</span>
<span class="fc" id="L54">    String SERVICE_NAME = ROLE;</span>

    /**
     * A constant for the HTTP &lt;code&gt;Accept-Language&lt;/code&gt; header.
     */
    String ACCEPT_LANGUAGE = &quot;Accept-Language&quot;;

    /**
     * Convenience method to get a ResourceBundle based on name and
     * HTTP &lt;code&gt;Accept-Language&lt;/code&gt; header.
     *
     * @param bundleName Name of bundle.
     * @param languageHeader A String with the language header.
     * @return A localized ResourceBundle.
     */
    ResourceBundle getBundle(String bundleName, String languageHeader);

    /**
     * Convenience method to get a ResourceBundle based on HTTP
     * Accept-Language header in HttpServletRequest.
     *
     * @param req The HTTP request to parse the
     * &lt;code&gt;Accept-Language&lt;/code&gt; of.
     * @return A localized ResourceBundle.
     */
    ResourceBundle getBundle(HttpServletRequest req);

    /**
     * Convenience method to get a &lt;code&gt;ResourceBundle&lt;/code&gt; based
     * on name and HTTP &lt;code&gt;Accept-Language&lt;/code&gt; header from a
     * &lt;code&gt;HttpServletRequest&lt;/code&gt;.
     *
     * @param bundleName Name of bundle.
     * @param req The HTTP request to parse the
     * &lt;code&gt;Accept-Language&lt;/code&gt; of.
     * @return A localized ResourceBundle.
     */
    ResourceBundle getBundle(String bundleName, HttpServletRequest req);

    /**
     * Attempts to pull the &lt;code&gt;Accept-Language&lt;/code&gt; header out of
     * the &lt;code&gt;HttpServletRequest&lt;/code&gt; object and then parse it.
     * If the header is not present, it will return a
     * &lt;code&gt;null&lt;/code&gt; &lt;code&gt;Locale&lt;/code&gt;.
     *
     * @param req The HTTP request to parse the
     * &lt;code&gt;Accept-Language&lt;/code&gt; of.
     * @return The parsed locale.
     */
    Locale getLocale(HttpServletRequest req);

    /**
     * Parses the &lt;code&gt;Accept-Language&lt;/code&gt; header and attempts to
     * create a &lt;code&gt;Locale&lt;/code&gt; from it.
     *
     * @param languageHeader The language header (i.e. &lt;code&gt;en, es;q=0.8,
     * zh-TW;q=0.1&lt;/code&gt;), or &lt;code&gt;null&lt;/code&gt; for the locale
     * corresponding to the default language and country.
     * @return The parsed locale, or a locale corresponding to the
     * language and country defaults.
     */
    Locale getLocale(String languageHeader);
}
</pre><div class="footer"><span class="right">Created with <a href="http://www.jacoco.org/jacoco">JaCoCo</a> 0.8.7.202105040129</span></div></body></html>