TPAC: Implement a locale picker
authorDan Scott <dscott@laurentian.ca>
Tue, 17 Jul 2012 21:37:54 +0000 (17:37 -0400)
committerLebbeous Fogle-Weekley <lebbeous@esilibrary.com>
Tue, 24 Jul 2012 21:25:30 +0000 (17:25 -0400)
In situations in which more than a single locale is configured, display
a locale picker in the TPAC header based on the registered locales. We
set the eg_locale cookie if passed a set_eg_locale GET param. Default
the selection to the currently selected locale (if any) and resubmit the
current page request.

Grabs the localized locale names, if available, from the database;
otherwise falls back to the en-US version of the locale names.

The locale picker form resubmits the current page with any variables
that were present in the current page request, so that switching locales
should still maintain state.

Signed-off-by: Dan Scott <dscott@laurentian.ca>
Signed-off-by: Lebbeous Fogle-Weekley <lebbeous@esilibrary.com>

Open-ILS/src/perlmods/lib/OpenILS/WWW/EGWeb.pm
Open-ILS/src/sql/Pg/002.schema.config.sql
Open-ILS/src/sql/Pg/upgrade/0723.function.get_locale_name.sql [new file with mode: 0644]
Open-ILS/src/templates/opac/parts/locale_picker.tt2 [new file with mode: 0644]
Open-ILS/src/templates/opac/parts/topnav.tt2
Open-ILS/web/css/skin/default/opac/style.css

index 66fb47e..34bb486 100644 (file)
@@ -8,14 +8,14 @@ use Encode;
 use Apache2::Const -compile => qw(OK DECLINED HTTP_INTERNAL_SERVER_ERROR);
 use Apache2::Log;
 use OpenSRF::EX qw(:try);
-use OpenILS::Utils::CStoreEditor;
+use OpenILS::Utils::CStoreEditor q/:funcs/;
 
 use constant OILS_HTTP_COOKIE_SKIN => 'eg_skin';
 use constant OILS_HTTP_COOKIE_THEME => 'eg_theme';
 use constant OILS_HTTP_COOKIE_LOCALE => 'eg_locale';
 
 # cache string bundles
-my @registered_locales;
+my %registered_locales;
 
 sub handler {
     my $r = shift;
@@ -152,7 +152,22 @@ sub load_context {
     my %locales = $r->dir_config->get('OILSWebLocale');
     load_locale_handlers($ctx, %locales);
 
-    $ctx->{locale} = 
+    $ctx->{locales} = \%registered_locales;
+
+    # Set a locale cookie if the requested locale is valid
+    my $set_locale = $cgi->param('set_eg_locale');
+    if (!(grep {$_ eq $set_locale} keys %registered_locales)) {
+        $set_locale = '';
+    } else {
+        my $slc = $cgi->cookie({
+            '-name' => OILS_HTTP_COOKIE_LOCALE,
+            '-value' => $set_locale,
+            '-expires' => '+10y'
+        });
+        $r->headers_out->add('Set-Cookie' => $slc);
+    }
+
+    $ctx->{locale} = $set_locale ||
         $cgi->cookie(OILS_HTTP_COOKIE_LOCALE) || 
         parse_accept_lang($r->headers_in->get('Accept-Language')) || 'en_us';
 
@@ -228,6 +243,7 @@ sub load_locale_handlers {
     my $ctx = shift;
     my %locales = @_;
 
+    my $editor = new_editor();
     my @locale_tags = sort { length($a) <=> length($b) } keys %locales;
 
     # always fall back to en_us, the assumed template language
@@ -236,7 +252,17 @@ sub load_locale_handlers {
     for my $idx (0..$#locale_tags) {
 
         my $tag = $locale_tags[$idx];
-        next if grep { $_ eq $tag } @registered_locales;
+        next if grep { $_ eq $tag } keys %registered_locales;
+
+        my $res = $editor->json_query({
+            "from" => [
+                "evergreen.get_locale_name",
+                $tag
+            ]
+        });
+
+        my $locale_name = $res->[0]->{"name"} if exists $res->[0]->{"name"};
+        next unless $locale_name;
 
         my $parent_tag = '';
         my $sub_idx = $idx;
@@ -272,7 +298,7 @@ sub load_locale_handlers {
         if ($@) {
             warn "$@\n" if $@;
         } else {
-            push(@registered_locales, $tag);
+            $registered_locales{"$tag"} = $locale_name;
         }
     }
 }
index 258aa50..7a48018 100644 (file)
@@ -87,7 +87,7 @@ CREATE TRIGGER no_overlapping_deps
     BEFORE INSERT OR UPDATE ON config.db_patch_dependencies
     FOR EACH ROW EXECUTE PROCEDURE evergreen.array_overlap_check ('deprecates');
 
-INSERT INTO config.upgrade_log (version, applied_to) VALUES ('0722', :eg_version); -- berick/mrpeters/senator
+INSERT INTO config.upgrade_log (version, applied_to) VALUES ('0723', :eg_version); -- denials/senator
 
 CREATE TABLE config.bib_source (
        id              SERIAL  PRIMARY KEY,
diff --git a/Open-ILS/src/sql/Pg/upgrade/0723.function.get_locale_name.sql b/Open-ILS/src/sql/Pg/upgrade/0723.function.get_locale_name.sql
new file mode 100644 (file)
index 0000000..b8c9b3d
--- /dev/null
@@ -0,0 +1,47 @@
+-- Evergreen DB patch 0723.schema.acq-po-state-constraint.sql
+--
+BEGIN;
+
+
+-- check whether patch can be applied
+SELECT evergreen.upgrade_deps_block_check('0723', :eg_version);
+
+CREATE OR REPLACE FUNCTION evergreen.get_locale_name(
+    IN locale TEXT,
+    OUT name TEXT,
+    OUT description TEXT
+) AS $$
+DECLARE
+    eg_locale TEXT;
+BEGIN
+    eg_locale := LOWER(SUBSTRING(locale FROM 1 FOR 2)) || '-' || UPPER(SUBSTRING(locale FROM 4 FOR 2));
+        
+    SELECT i18nc.string INTO name
+    FROM config.i18n_locale i18nl
+       INNER JOIN config.i18n_core i18nc ON i18nl.code = i18nc.translation
+    WHERE i18nc.identity_value = eg_locale
+       AND code = eg_locale
+       AND i18nc.fq_field = 'i18n_l.name';
+
+    IF name IS NULL THEN
+       SELECT i18nl.name INTO name
+       FROM config.i18n_locale i18nl
+       WHERE code = eg_locale;
+    END IF;
+
+    SELECT i18nc.string INTO description
+    FROM config.i18n_locale i18nl
+       INNER JOIN config.i18n_core i18nc ON i18nl.code = i18nc.translation
+    WHERE i18nc.identity_value = eg_locale
+       AND code = eg_locale
+       AND i18nc.fq_field = 'i18n_l.description';
+
+    IF description IS NULL THEN
+       SELECT i18nl.description INTO description
+       FROM config.i18n_locale i18nl
+       WHERE code = eg_locale;
+    END IF;
+END;
+$$ LANGUAGE PLPGSQL COST 1 STABLE;
+
+COMMIT;
diff --git a/Open-ILS/src/templates/opac/parts/locale_picker.tt2 b/Open-ILS/src/templates/opac/parts/locale_picker.tt2
new file mode 100644 (file)
index 0000000..c3943a6
--- /dev/null
@@ -0,0 +1,23 @@
+[%- IF ctx.locales.keys.size > 1;
+    set_locale = CGI.param('set_eg_locale') || CGI.cookie('eg_locale');
+%]
+<form id="locale_picker_form" action="[% mkurl() %]">
+    <label for="locale_picker">[% l("Language:") %]</label>
+    [%- FOREACH param IN CGI.params(); -%]
+        [%- NEXT IF param.key == 'set_eg_locale'; -%]
+        <input type="hidden" name="[% param.key %]" value="[% param.value %]" />
+    [%- END; -%]
+    <select id="locale_picker" name="set_eg_locale">
+    [%- FOREACH locale IN ctx.locales.keys %]
+        [%- IF set_locale == locale;
+                selected = 'selected="selected"';
+            ELSE;
+                selected = '';
+            END;
+        %]
+        <option value="[% locale | html %]" [% selected %]>[% ctx.locales.$locale | html %]</option>
+    [%- END %]
+    </select>
+    <input type="submit" value="[% l("Change") %]" />
+</form>
+[%- END %]
index beaccb8..832205d 100644 (file)
@@ -53,6 +53,7 @@
         </div>
         [% END %]
     </div>
+    [%- INCLUDE "opac/parts/locale_picker.tt2" %]
     <div class="common-no-pad"></div>
 </div>
 </div>
index a8fb879..9aa2ba7 100644 (file)
@@ -1537,3 +1537,15 @@ a.preflib_change {
     border-bottom-style: solid;
 }
     
+#locale_picker_form {
+    float: right;
+    padding: 0.5em 1em 0.5em 0;
+    border-right: thin #69A088 solid;
+}
+
+#locale_picker_form * {
+    margin: 0;
+    padding: 0;
+    vertical-align: middle;
+    font-size: 1em;
+}