- remember me cookie security improvement (the time when the cookie was generated is saved and checked in range [now-remember_me_length; now]

- tags improvements
 * pass to templates all fields in table #tags (handy for plugins such as type tags)
 * fix issue with tag letter when first letter is accentuated (utf-8)
 * tags are sorted on url_name instead of name (accentuated first letter chars are the same as without accent)
 * better use of columns in by letter display mode

git-svn-id: http://piwigo.org/svn/trunk@2409 68402e56-0260-453c-a942-63ccdbb3a9ee
This commit is contained in:
rvelices 2008-07-01 02:09:21 +00:00
parent 1d3706a421
commit d91d0ac444
11 changed files with 149 additions and 175 deletions

View file

@ -275,7 +275,6 @@ if (count($page['cat_elements_id']) > 0)
{ {
// remove tags // remove tags
$tags = get_common_tags($page['cat_elements_id'], -1); $tags = get_common_tags($page['cat_elements_id'], -1);
usort($tags, 'name_compare');
$template->assign( $template->assign(
array( array(

View file

@ -550,6 +550,11 @@ function name_compare($a, $b)
return strcmp(strtolower($a['name']), strtolower($b['name'])); return strcmp(strtolower($a['name']), strtolower($b['name']));
} }
function tag_alpha_compare($a, $b)
{
return strcmp(strtolower($a['url_name']), strtolower($b['url_name']));
}
/** /**
* exits the current script (either exit or redirect) * exits the current script (either exit or redirect)
*/ */
@ -732,7 +737,7 @@ function render_category_literal_description($desc)
return strip_tags($desc, '<span><p><a><br><b><i><small><big><strong><em>'); return strip_tags($desc, '<span><p><a><br><b><i><small><big><strong><em>');
} }
/** returns the argument_ids array with new sequenced keys based on related /** returns the argument_ids array with new sequenced keys based on related
* names. Sequence is not case sensitive. * names. Sequence is not case sensitive.
* Warning: By definition, this function breaks original keys * Warning: By definition, this function breaks original keys
*/ */

View file

@ -59,7 +59,7 @@ SELECT tag_id, COUNT(DISTINCT(it.image_id)) counter
} }
$query = ' $query = '
SELECT id, name, url_name SELECT *
FROM '.TAGS_TABLE; FROM '.TAGS_TABLE;
$result = pwg_query($query); $result = pwg_query($query);
$tags = array(); $tags = array();
@ -83,9 +83,7 @@ SELECT id, name, url_name
function get_all_tags() function get_all_tags()
{ {
$query = ' $query = '
SELECT id, SELECT *
name,
url_name
FROM '.TAGS_TABLE.' FROM '.TAGS_TABLE.'
;'; ;';
$result = pwg_query($query); $result = pwg_query($query);
@ -95,7 +93,7 @@ SELECT id,
array_push($tags, $row); array_push($tags, $row);
} }
usort($tags, 'name_compare'); usort($tags, 'tag_alpha_compare');
return $tags; return $tags;
} }
@ -227,9 +225,9 @@ function get_common_tags($items, $max_tags, $excluded_tag_ids=null)
return array(); return array();
} }
$query = ' $query = '
SELECT id, name, url_name, count(*) counter SELECT t.*, count(*) counter
FROM '.IMAGE_TAG_TABLE.' FROM '.IMAGE_TAG_TABLE.'
INNER JOIN '.TAGS_TABLE.' ON tag_id = id INNER JOIN '.TAGS_TABLE.' t ON tag_id = id
WHERE image_id IN ('.implode(',', $items).')'; WHERE image_id IN ('.implode(',', $items).')';
if (!empty($excluded_tag_ids)) if (!empty($excluded_tag_ids))
{ {
@ -256,7 +254,7 @@ SELECT id, name, url_name, count(*) counter
{ {
array_push($tags, $row); array_push($tags, $row);
} }
usort($tags, 'name_compare'); usort($tags, 'tag_alpha_compare');
return $tags; return $tags;
} }
@ -307,7 +305,7 @@ function find_tags($ids, $url_names=array(), $names=array() )
} }
$query = ' $query = '
SELECT id, url_name, name SELECT *
FROM '.TAGS_TABLE.' FROM '.TAGS_TABLE.'
WHERE '. implode( ' WHERE '. implode( '
OR ', $where_clauses); OR ', $where_clauses);

View file

@ -838,32 +838,7 @@ function get_default_template()
*/ */
function get_default_language() function get_default_language()
{ {
global $conf; return get_default_user_value('language', PHPWG_DEFAULT_LANGUAGE);
if (isset($conf['browser_language']) and $conf['browser_language'])
{
return get_browser_language();
}
else
{
return get_default_user_value('language', PHPWG_DEFAULT_LANGUAGE);
}
}
/*
* Returns the browser language value
*
*/
function get_browser_language()
{
$browser_language = substr($_SERVER["HTTP_ACCEPT_LANGUAGE"], 0, 2);
foreach (get_languages() as $language_code => $language_name)
{
if (substr($language_code, 0, 2) == $browser_language)
{
return $language_code;
}
}
return PHPWG_DEFAULT_LANGUAGE;
} }
/** /**
@ -923,7 +898,6 @@ function create_user_infos($arg_id, $override_values = null)
{ {
$status = 'normal'; $status = 'normal';
} }
$default_user['language'] = get_default_language();
$insert = array_merge( $insert = array_merge(
$default_user, $default_user,
@ -974,9 +948,10 @@ SELECT name
/** /**
* returns the auto login key or false on error * returns the auto login key or false on error
* @param int user_id * @param int user_id
* @param time_t time
* @param string [out] username * @param string [out] username
*/ */
function calculate_auto_login_key($user_id, &$username) function calculate_auto_login_key($user_id, $time, &$username)
{ {
global $conf; global $conf;
$query = ' $query = '
@ -989,7 +964,7 @@ WHERE '.$conf['user_fields']['id'].' = '.$user_id;
{ {
$row = mysql_fetch_assoc($result); $row = mysql_fetch_assoc($result);
$username = $row['username']; $username = $row['username'];
$data = $row['username'].$row['password']; $data = $time.$row['username'].$row['password'];
$key = base64_encode( $key = base64_encode(
pack('H*', sha1($data)) pack('H*', sha1($data))
.hash_hmac('md5', $data, $conf['secret_key'],true) .hash_hmac('md5', $data, $conf['secret_key'],true)
@ -1011,12 +986,13 @@ function log_user($user_id, $remember_me)
if ($remember_me and $conf['authorize_remembering']) if ($remember_me and $conf['authorize_remembering'])
{ {
$key = calculate_auto_login_key($user_id, $username); $now = time();
$key = calculate_auto_login_key($user_id, $now, $username);
if ($key!==false) if ($key!==false)
{ {
$cookie = array('id' => (int)$user_id, 'key' => $key); $cookie = $user_id.'-'.$now.'-'.$key;
setcookie($conf['remember_me_name'], setcookie($conf['remember_me_name'],
serialize($cookie), $cookie,
time()+$conf['remember_me_length'], time()+$conf['remember_me_length'],
cookie_path() cookie_path()
); );
@ -1049,13 +1025,17 @@ function auto_login() {
if ( isset( $_COOKIE[$conf['remember_me_name']] ) ) if ( isset( $_COOKIE[$conf['remember_me_name']] ) )
{ {
$cookie = unserialize(stripslashes($_COOKIE[$conf['remember_me_name']])); $cookie = explode('-', stripslashes($_COOKIE[$conf['remember_me_name']]));
if ($cookie!==false and is_numeric(@$cookie['id']) ) if ( count($cookie)===3
and is_numeric(@$cookie[0]) /*user id*/
and is_numeric(@$cookie[1]) /*time*/
and time()-$conf['remember_me_length']<=@$cookie[1]
and time()>=@$cookie[1] /*cookie generated in the past*/ )
{ {
$key = calculate_auto_login_key( $cookie['id'], $username ); $key = calculate_auto_login_key( $cookie[0], $cookie[1], $username );
if ($key!==false and $key===$cookie['key']) if ($key!==false and $key===$cookie[2])
{ {
log_user($cookie['id'], true); log_user($cookie[0], true);
trigger_action('login_success', $username); trigger_action('login_success', $username);
return true; return true;
} }

View file

@ -111,29 +111,23 @@ if ('tags' == @$page['section'])
{ {
$template->append( $template->append(
'related_tags', 'related_tags',
array( array_merge( $tag,
'U_TAG' => make_index_url( array(
array( 'URL' => make_index_url(
'tags' => array($tag) array(
) 'tags' => array($tag)
), )
),
'NAME' => $tag['name'], 'U_ADD' => make_index_url(
array(
'CLASS' => 'tagLevel'.$tag['level'], 'tags' => array_merge(
$page['tags'],
'add' => array( array($tag)
)
'URL' => make_index_url(
array(
'tags' => array_merge(
$page['tags'],
array($tag)
) )
) ),
), )
'COUNTER' => $tag['counter'],
)
) )
); );
} }

View file

@ -889,7 +889,7 @@ function ws_tags_getList($params, &$service)
} }
else else
{ {
usort($tags, 'name_compare'); usort($tags, 'tag_alpha_compare');
} }
for ($i=0; $i<count($tags); $i++) for ($i=0; $i<count($tags); $i++)
{ {

View file

@ -186,7 +186,7 @@ $available_tags = get_available_tags();
if (count($available_tags) > 0) if (count($available_tags) > 0)
{ {
usort( $available_tags, 'name_compare'); usort( $available_tags, 'tag_alpha_compare');
$template->assign( $template->assign(
'TAG_SELECTION', 'TAG_SELECTION',

View file

@ -84,12 +84,12 @@ $tags = get_available_tags();
if ($page['display_mode'] == 'letters') { if ($page['display_mode'] == 'letters') {
// we want tags diplayed in alphabetic order // we want tags diplayed in alphabetic order
usort($tags, 'name_compare'); usort($tags, 'tag_alpha_compare');
$current_letter = null; $current_letter = null;
$is_first_tag = true;
$nb_tags = count($tags); $nb_tags = count($tags);
$current_column_tags = 0; $current_column = 1;
$current_tag_idx = 0;
$letter = array( $letter = array(
'tags' => array() 'tags' => array()
@ -97,21 +97,21 @@ if ($page['display_mode'] == 'letters') {
foreach ($tags as $tag) foreach ($tags as $tag)
{ {
$tag_letter = strtoupper(substr($tag['name'], 0, 1)); $tag_letter = strtoupper(substr($tag['url_name'], 0, 1));
if ($is_first_tag) { if ($current_tag_idx==0) {
$current_letter = $tag_letter; $current_letter = $tag_letter;
$letter['TITLE'] = $tag_letter; $letter['TITLE'] = $tag_letter;
$is_first_tag = false;
} }
//lettre precedente differente de la lettre suivante //lettre precedente differente de la lettre suivante
if ($tag_letter !== $current_letter) if ($tag_letter !== $current_letter)
{ {
if ($current_column_tags > $nb_tags/$conf['tag_letters_column_number']) if ($current_column<$conf['tag_letters_column_number']
and $current_tag_idx > $current_column*$nb_tags/$conf['tag_letters_column_number'] )
{ {
$letter['CHANGE_COLUMN'] = true; $letter['CHANGE_COLUMN'] = true;
$current_column_tags = 0; $current_column++;
} }
$letter['TITLE'] = $current_letter; $letter['TITLE'] = $current_letter;
@ -120,7 +120,7 @@ if ($page['display_mode'] == 'letters') {
'letters', 'letters',
$letter $letter
); );
$current_letter = $tag_letter; $current_letter = $tag_letter;
$letter = array( $letter = array(
'tags' => array() 'tags' => array()
@ -129,18 +129,19 @@ if ($page['display_mode'] == 'letters') {
array_push( array_push(
$letter['tags'], $letter['tags'],
array( array_merge(
'URL' => make_index_url( $tag,
array( array(
'tags' => array($tag), 'URL' => make_index_url(
) array(
), 'tags' => array($tag),
'NAME' => $tag['name'], )
'COUNTER' => $tag['counter'], ),
)
) )
); );
$current_column_tags++; $current_tag_idx++;
} }
// flush last letter // flush last letter
@ -168,23 +169,22 @@ $tags = array_slice($tags, 0, $conf['full_tag_cloud_items_number']);
$tags = add_level_to_tags($tags); $tags = add_level_to_tags($tags);
// we want tags diplayed in alphabetic order // we want tags diplayed in alphabetic order
usort($tags, 'name_compare'); usort($tags, 'tag_alpha_compare');
// display sorted tags // display sorted tags
foreach ($tags as $tag) foreach ($tags as $tag)
{ {
$template->append( $template->append(
'tags', 'tags',
array( array_merge(
'URL' => make_index_url( $tag,
array( array(
'tags' => array($tag), 'URL' => make_index_url(
) array(
), 'tags' => array($tag),
)
'NAME' => $tag['name'], ),
'TITLE' => $tag['counter'], )
'CLASS' => 'tagLevel'.$tag['level'],
) )
); );
} }

View file

@ -1,34 +1,32 @@
#menubar { #menubar {
float: left; float: left;
margin: 0 0 10px 1em; margin: 0 0 10px 1em;
padding: 0; padding: 0;
/* Fix against the "double margin of a floated item" IE bug */ display: inline;
/* Damned: that screws up top_navbar in opera 7.54/Linux! */ text-align: left; /* follow-up of the "be nice to IE5" rule */
display: inline;
text-align: left; /* follow-up of the "be nice to IE5" rule */
} }
#menubar DL, #menubar DT, #menubar DD { #menubar DL, #menubar DT, #menubar DD {
margin: 0; padding: 0; display: block; margin: 0; padding: 0; display: block;
} }
#menubar .button { #menubar .button {
margin: 0 2px; margin: 0 2px;
width: auto; width: auto;
padding: 0; padding: 0;
text-indent: 0; text-indent: 0;
list-style: none; list-style: none;
text-align: center; text-align: center;
float: right; float: right;
} }
/* H2 properties copied here */ /* H2 properties copied here */
#menubar DT { #menubar DT {
font-weight: bold; /* default for h2 */ font-weight: bold;
margin: 0; margin: 0;
padding: 5px 5px 5px 5px; padding: 5px 5px 5px 5px;
font-size: 120%; font-size: 120%;
text-align: center; text-align: center;
} }
#menubar UL, #menubar UL,
@ -36,26 +34,26 @@
#menubar FORM, #menubar FORM,
#menubar P, /* ooh, careful... */ #menubar P, /* ooh, careful... */
#menubar .totalImages { #menubar .totalImages {
font-size: 92%; font-size: 92%;
margin: 10px 0 10px 10px; margin: 10px 0 10px 10px;
} }
#menubar UL { #menubar UL {
list-style-type: square; list-style-type: square;
list-style-position: inside; list-style-position: inside;
padding: 0 0 0 2px; padding: 0 0 0 2px;
} }
#menubar UL UL { #menubar UL UL {
font-size: 100%; font-size: 100%;
margin-top: 0; margin-top: 0;
margin-bottom: 0; margin-bottom: 0;
} }
#menubar LI.selected A { #menubar LI.selected A {
font-weight: bold; font-weight: bold;
} }
#menubar LI.selected LI A { #menubar LI.selected LI A {
font-weight: normal; font-weight: normal;
} }
#menubar .menuInfoCatByChild { #menubar .menuInfoCatByChild {
@ -64,86 +62,86 @@
} }
#menubar HR { #menubar HR {
display: block; display: block;
margin: 10px auto; margin: 10px auto;
width: 90%; width: 90%;
} }
#menubar INPUT { #menubar INPUT {
text-indent: 2px; text-indent: 2px;
} }
/* quickconnect form */ /* quickconnect form */
FORM#quickconnect { FORM#quickconnect {
margin: 0; margin: 0;
padding: 5px; padding: 5px;
} }
FORM#quickconnect FIELDSET { FORM#quickconnect FIELDSET {
margin: 0; margin: 0;
padding: 0 0 0.5em 0; padding: 0 0 0.5em 0;
} }
FORM#quickconnect P { FORM#quickconnect P {
margin-left: 0; margin-left: 0;
font-size: 100%; font-size: 100%;
float: left; float: left;
clear: left; clear: left;
} }
FORM#quickconnect P INPUT { FORM#quickconnect P INPUT {
margin: 0; margin: 0;
} }
FORM#quickconnect UL.actions { FORM#quickconnect UL.actions {
display: inline; display: inline;
float: right; float: right;
padding: 0; padding: 0;
text-align: right; /* Opera 7.5 */ text-align: right; /* Opera 7.5 */
} }
FORM#quickconnect FIELDSET>UL.actions { FORM#quickconnect FIELDSET>UL.actions {
width: 40%; /* Opera 7.5 cannot find why width:auto fails :-( */ width: 40%; /* Opera 7.5 cannot find why width:auto fails :-( */
} }
FORM#quickconnect UL.actions, FORM#quickconnect UL.actions,
FORM#quickconnect P, FORM#quickconnect P,
FORM#quickconnect LABEL { FORM#quickconnect LABEL {
padding: 0 0.5em 0 0.5em; padding: 0 0.5em 0 0.5em;
} }
FORM#quickconnect LABEL { FORM#quickconnect LABEL {
margin:0; margin:0;
width: 100%; width: 100%;
box-sizing: border-box; /* CSS3 */ box-sizing: border-box; /* CSS3 */
} }
FORM#quickconnect INPUT[type=text], FORM#quickconnect INPUT[type=text],
FORM#quickconnect INPUT[type=password] { FORM#quickconnect INPUT[type=password] {
width: 100%; /* mozilla can handle 100% */ width: 100%; /* mozilla can handle 100% */
} }
/* same as above for IE with inputfix.htc */ /* same as above for IE with inputfix.htc
/* unfortunately IE doesn't handle that correctly */ unfortunately IE doesn't handle that correctly
/* so you should set a width in em in local_layout.css */ so you should set a width in em in local_layout.css */
/*FORM#quickconnect INPUT.text, /*FORM#quickconnect INPUT.text,
FORM#quickconnect INPUT.password { FORM#quickconnect INPUT.password {
width: 95%; width: 95%;
}*/ }*/
FORM#quicksearch { FORM#quicksearch {
margin-top: 4px; margin-top: 4px;
margin-bottom: 1px; margin-bottom: 1px;
} }
input#qsearchInput { INPUT#qsearchInput {
width: 90%; width: 90%;
} }
#menubar #mbMenu p { margin: 0px; padding: 0px; } #menubar #mbMenu p { margin: 0px; padding: 0px; }
#menubar #menuTagCloud { #menubar #menuTagCloud {
text-align: center; text-align: center;
margin: 5px 0; margin: 5px 0;
} }
#menubar #menuTagCloud LI #menubar #menuTagCloud LI
{ {
display: inline; display: inline;
white-space: nowrap; /* No line break in the LI but Opera set nowrap to */ white-space: nowrap; /* No line break in the LI but Opera set nowrap to */
} }

View file

@ -21,10 +21,10 @@
{/if}{*links*} {/if}{*links*}
{if isset($U_START_FILTER)} {if isset($U_START_FILTER)}
<a href="{$U_START_FILTER}" title="{'start_filter_hint'|@translate}" rel="nofollow"><img src="{$ROOT_URL}{$themeconf.icon_dir}/start_filter.png" class="button" alt="{'start_filter_hint'|@translate}"></a> <a href="{$U_START_FILTER}" title="{'start_filter_hint'|@translate}" rel="nofollow"><img src="{$ROOT_URL}{$themeconf.icon_dir}/start_filter.png" class="button" alt="start filter"></a>
{/if} {/if}
{if isset($U_STOP_FILTER)} {if isset($U_STOP_FILTER)}
<a href="{$U_STOP_FILTER}" title="{'stop_filter_hint'|@translate}"><img src="{$ROOT_URL}{$themeconf.icon_dir}/stop_filter.png" class="button" alt="{'stop_filter_hint'|@translate}"></a> <a href="{$U_STOP_FILTER}" title="{'stop_filter_hint'|@translate}"><img src="{$ROOT_URL}{$themeconf.icon_dir}/stop_filter.png" class="button" alt="stop filter"></a>
{/if} {/if}
<dl id="mbCategories"> <dl id="mbCategories">
@ -48,14 +48,14 @@
<ul id="menuTagCloud"> <ul id="menuTagCloud">
{foreach from=$related_tags item=tag} {foreach from=$related_tags item=tag}
<li> <li>
{if !empty($tag.add) } {if !empty($tag.U_ADD) }
<a href="{$tag.add.URL}" <a href="{$tag.U_ADD}"
title="{$pwg->l10n_dec('%d element are also linked to current tags', '%d elements are also linked to current tags', $tag.add.COUNTER)}" title="{$pwg->l10n_dec('%d element are also linked to current tags', '%d elements are also linked to current tags', $tag.counter)}"
rel="nofollow"> rel="nofollow">
<img src="{$ROOT_URL}{$themeconf.icon_dir}/add_tag.png" alt="+" /> <img src="{$ROOT_URL}{$themeconf.icon_dir}/add_tag.png" alt="+" />
</a> </a>
{/if} {/if}
<a href="{$tag.U_TAG}" class="{$tag.CLASS}" title="{'See elements linked to this tag only'|@translate}">{$tag.NAME}</a> <a href="{$tag.URL}" class="tagLevel{$tag.level}" title="{'See elements linked to this tag only'|@translate}">{$tag.name}</a>
</li> </li>
{/foreach} {/foreach}
</ul> </ul>

View file

@ -20,7 +20,7 @@
{if $display_mode == 'cloud'} {if $display_mode == 'cloud'}
<ul id="fullTagCloud"> <ul id="fullTagCloud">
{foreach from=$tags item=tag} {foreach from=$tags item=tag}
<li><a href="{$tag.URL}" class="{$tag.CLASS}" title="{$tag.TITLE}">{$tag.NAME}</a></li> <li><a href="{$tag.URL}" class="tagLevel{$tag.level}" title="{$tag.counter}">{$tag.name}</a></li>
{/foreach} {/foreach}
</ul> </ul>
{/if} {/if}
@ -35,8 +35,8 @@
<table class="tagLetterContent"> <table class="tagLetterContent">
{foreach from=$letter.tags item=tag} {foreach from=$letter.tags item=tag}
<tr class="tagLine"> <tr class="tagLine">
<td><a href="{$tag.URL}">{$tag.NAME}</a></td> <td><a href="{$tag.URL}">{$tag.name}</a></td>
<td class="nbEntries">{$pwg->l10n_dec('%d element', '%d elements', $tag.COUNTER)}</td> <td class="nbEntries">{$pwg->l10n_dec('%d element', '%d elements', $tag.counter)}</td>
</tr> </tr>
{/foreach} {/foreach}
</table> </table>
@ -52,4 +52,4 @@
{/if} {/if}
{/if} {/if}
</div> <!-- content --> </div> <!-- content -->