Annotation of loncom/interface/lonpreferences.pm, revision 1.151
1.1 www 1: # The LearningOnline Network
2: # Preferences
3: #
1.151 ! bisitz 4: # $Id: lonpreferences.pm,v 1.150 2009/04/05 17:18:29 droeschl Exp $
1.2 albertel 5: #
6: # Copyright Michigan State University Board of Trustees
7: #
8: # This file is part of the LearningOnline Network with CAPA (LON-CAPA).
9: #
10: # LON-CAPA is free software; you can redistribute it and/or modify
11: # it under the terms of the GNU General Public License as published by
12: # the Free Software Foundation; either version 2 of the License, or
13: # (at your option) any later version.
14: #
15: # LON-CAPA is distributed in the hope that it will be useful,
16: # but WITHOUT ANY WARRANTY; without even the implied warranty of
17: # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18: # GNU General Public License for more details.
19: #
20: # You should have received a copy of the GNU General Public License
21: # along with LON-CAPA; if not, write to the Free Software
22: # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
23: #
24: # /home/httpd/html/adm/gpl.txt
25: #
26: # http://www.lon-capa.org/
27: #
1.3 matthew 28: # This package uses the "londes.js" javascript code.
29: #
30: # TODOs that have to be completed:
31: # interface with lonnet to change the password
32:
1.1 www 33: package Apache::lonpreferences;
34:
35: use strict;
1.86 albertel 36: use LONCAPA;
1.1 www 37: use Apache::Constants qw(:common);
1.3 matthew 38: use Apache::File;
39: use Crypt::DES;
40: use DynaLoader; # for Crypt::DES version
1.4 matthew 41: use Apache::loncommon();
1.23 matthew 42: use Apache::lonhtmlcommon();
1.32 www 43: use Apache::lonlocal;
1.59 albertel 44: use Apache::lonnet;
1.95 albertel 45: use LONCAPA();
1.3 matthew 46:
47: #
48: # Write lonnet::passwd to do the call below.
49: # Use:
50: # my $answer=reply("encrypt:passwd:$udom:$uname:$upass",$tryserver);
51: #
52: ##################################################
53: # password associated functions #
54: ##################################################
55: sub des_keys {
1.4 matthew 56: # Make a new key for DES encryption.
1.36 www 57: # Each key has two parts which are returned separately.
1.4 matthew 58: # Please note: Each key must be passed through the &hex function
59: # before it is output to the web browser. The hex versions cannot
60: # be used to decrypt.
1.3 matthew 61: my @hexstr=('0','1','2','3','4','5','6','7',
62: '8','9','a','b','c','d','e','f');
63: my $lkey='';
64: for (0..7) {
65: $lkey.=$hexstr[rand(15)];
66: }
67: my $ukey='';
68: for (0..7) {
69: $ukey.=$hexstr[rand(15)];
70: }
71: return ($lkey,$ukey);
72: }
73:
74: sub des_decrypt {
75: my ($key,$cyphertext) = @_;
76: my $keybin=pack("H16",$key);
77: my $cypher;
78: if ($Crypt::DES::VERSION>=2.03) {
79: $cypher=new Crypt::DES $keybin;
80: } else {
81: $cypher=new DES $keybin;
82: }
83: my $plaintext=
84: $cypher->decrypt(unpack("a8",pack("H16",substr($cyphertext,0,16))));
85: $plaintext.=
86: $cypher->decrypt(unpack("a8",pack("H16",substr($cyphertext,16,16))));
1.4 matthew 87: $plaintext=substr($plaintext,1,ord(substr($plaintext,0,1)) );
1.3 matthew 88: return $plaintext;
89: }
90:
1.4 matthew 91: ################################################################
92: # Handler subroutines #
93: ################################################################
1.9 matthew 94:
95: ################################################################
1.28 www 96: # Language Change Subroutines #
97: ################################################################
1.44 www 98:
99: sub wysiwygchanger {
100: my $r = shift;
1.126 droeschl 101: Apache::lonhtmlcommon::add_breadcrumb(
102: { href => '/adm/preferences?action=changewysiwyg',
103: text => 'Change WYSIWYG Preferences'});
1.147 schafran 104: $r->print(Apache::loncommon::start_page('Content Display Settings'));
1.126 droeschl 105: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change WYSIWYG Preferences'));
106:
1.44 www 107: my %userenv = &Apache::lonnet::get
108: ('environment',['wysiwygeditor']);
1.78 albertel 109: my $onselect='checked="checked"';
1.44 www 110: my $offselect='';
1.77 albertel 111: if ($userenv{'wysiwygeditor'} eq 'on') {
1.44 www 112: $onselect='';
1.78 albertel 113: $offselect='checked="checked"';
1.44 www 114: }
115: my $switchoff=&mt('Disable WYSIWYG editor');
116: my $switchon=&mt('Enable WYSIWYG editor');
1.124 www 117: my $warning='';
118: if ($env{'user.adv'}) {
119: $warning.="<p>".&mt("The WYSIWYG editor only supports simple HTML and is in many cases unsuited for advanced authoring. In a number of cases, it may destroy advanced authoring involving LaTeX and script function calls.")."</p>";
120: }
1.44 www 121: $r->print(<<ENDLSCREEN);
1.88 albertel 122: <form name="prefs" action="/adm/preferences" method="post">
1.44 www 123: <input type="hidden" name="action" value="set_wysiwyg" />
1.124 www 124: $warning
1.44 www 125: <br />
1.65 albertel 126: <label><input type="radio" name="wysiwyg" value="off" $onselect /> $switchoff</label><br />
127: <label><input type="radio" name="wysiwyg" value="on" $offselect /> $switchon</label>
1.44 www 128: ENDLSCREEN
1.136 schafran 129: $r->print('<br /><input type="submit" value="'.&mt('Save').'" />');
1.44 www 130: }
131:
132:
133: sub verify_and_change_wysiwyg {
134: my $r = shift;
1.59 albertel 135: my $newsetting=$env{'form.wysiwyg'};
1.44 www 136: &Apache::lonnet::put('environment',{'wysiwygeditor' => $newsetting});
1.116 raeburn 137: &Apache::lonnet::appenv({'environment.wysiwygeditor' => $newsetting});
1.126 droeschl 138: # $r->print('<p>'.&mt('Setting WYSIWYG editor to:').' '.&mt($newsetting).'</p>');
139: print_main_menu($r,'<p>'.&mt('Setting WYSIWYG editor to:').' '
140: .&mt($newsetting).'</p>');
1.44 www 141: }
142:
143: ################################################################
144: # Language Change Subroutines #
145: ################################################################
1.28 www 146: sub languagechanger {
147: my $r = shift;
1.126 droeschl 148:
149: Apache::lonhtmlcommon::add_breadcrumb(
150: { href => '/adm/preferences?action=changelanguages',
1.127 droeschl 151: text => 'Change Language'});
1.147 schafran 152: $r->print(Apache::loncommon::start_page('Content Display Settings'));
1.126 droeschl 153: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Language'));
1.59 albertel 154: my $user = $env{'user.name'};
155: my $domain = $env{'user.domain'};
1.28 www 156: my %userenv = &Apache::lonnet::get
1.32 www 157: ('environment',['languages']);
1.29 www 158: my $language=$userenv{'languages'};
1.32 www 159:
1.33 www 160: my $pref=&mt('Preferred language');
161: my %langchoices=('' => 'No language preference');
162: foreach (&Apache::loncommon::languageids()) {
163: if (&Apache::loncommon::supportedlanguagecode($_)) {
164: $langchoices{&Apache::loncommon::supportedlanguagecode($_)}
165: = &Apache::loncommon::plainlanguagedescription($_);
166: }
167: }
168: my $selectionbox=&Apache::loncommon::select_form($language,'language',
169: %langchoices);
1.28 www 170: $r->print(<<ENDLSCREEN);
1.88 albertel 171: <form name="prefs" action="/adm/preferences" method="post">
1.28 www 172: <input type="hidden" name="action" value="verify_and_change_languages" />
1.33 www 173: <br />$pref: $selectionbox
1.28 www 174: ENDLSCREEN
1.136 schafran 175: $r->print('<br /><input type="submit" value="'.&mt('Save').'" />');
1.28 www 176: }
177:
178:
179: sub verify_and_change_languages {
180: my $r = shift;
1.59 albertel 181: my $user = $env{'user.name'};
182: my $domain = $env{'user.domain'};
1.28 www 183: # Screenname
1.59 albertel 184: my $newlanguage = $env{'form.language'};
1.28 www 185: $newlanguage=~s/[^\-\w]//g;
186: my $message='';
187: if ($newlanguage) {
1.29 www 188: &Apache::lonnet::put('environment',{'languages' => $newlanguage});
1.116 raeburn 189: &Apache::lonnet::appenv({'environment.languages' => $newlanguage});
1.110 bisitz 190: $message=&mt('Set new preferred languages to ').'<tt>"'.$newlanguage.'"</tt>.';
1.28 www 191: } else {
1.29 www 192: &Apache::lonnet::del('environment',['languages']);
1.139 raeburn 193: &Apache::lonnet::delenv('environment.languages');
1.110 bisitz 194: $message=&mt('Reset preferred language.');
1.28 www 195: }
1.132 raeburn 196: &Apache::loncommon::flush_langs_cache($user,$domain);
1.126 droeschl 197: print_main_menu($r, $message);
198: # $r->print(<<ENDVCSCREEN);
199: #$message
200: #ENDVCSCREEN
1.28 www 201: }
202:
1.50 albertel 203: ################################################################
1.54 albertel 204: # Tex Engine Change Subroutines #
205: ################################################################
206: sub texenginechanger {
207: my $r = shift;
1.126 droeschl 208: Apache::lonhtmlcommon::add_breadcrumb(
209: { href => '/adm/preferences?action=changetexenginepref',
210: text => 'Change How Math Equations Are Displayed'});
1.147 schafran 211: $r->print(Apache::loncommon::start_page('Content Display Settings'));
1.126 droeschl 212: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change How Math Equations Are Displayed'));
1.59 albertel 213: my $user = $env{'user.name'};
214: my $domain = $env{'user.domain'};
1.54 albertel 215: my %userenv = &Apache::lonnet::get('environment',['texengine']);
216: my $texengine=$userenv{'texengine'};
217:
1.69 albertel 218: my %mathchoices=('' => 'Default',
1.123 bisitz 219: 'tth' => 'tth (TeX to HTML)',
1.64 albertel 220: #'ttm' => 'TeX to MathML',
1.54 albertel 221: 'jsMath' => 'jsMath',
1.123 bisitz 222: 'mimetex' => 'mimetex (Convert to Images)'
1.54 albertel 223: );
224: my $selectionbox=&Apache::loncommon::select_form($texengine,'texengine',
225: %mathchoices);
1.67 albertel 226: my $jsMath_start=&Apache::lontexconvert::jsMath_header();
1.123 bisitz 227: my %lt=&Apache::lonlocal::texthash(
228: 'headline' => 'Change Math Preferences',
229: 'preftxt' => 'Preferred method to display Math',
1.136 schafran 230: 'change' => 'Save',
1.123 bisitz 231: 'exmpl' => 'Examples',
232: 'jsmath' => 'jsMath:',
233: 'tth' => 'tth (TeX to HTML):',
234: 'mimetex' => 'mimetex (Convert to Images):',
235: );
236:
1.54 albertel 237: $r->print(<<ENDLSCREEN);
1.123 bisitz 238: <h2>$lt{'headline'}</h2>
1.88 albertel 239: <form name="prefs" action="/adm/preferences" method="post">
1.54 albertel 240: <input type="hidden" name="action" value="verify_and_change_texengine" />
1.123 bisitz 241: <p>
1.136 schafran 242: $lt{'preftxt'}: $selectionbox
243: <br />
244: <input type="submit" value="$lt{'change'}" />
1.123 bisitz 245: </p>
1.54 albertel 246: </form>
1.123 bisitz 247: <br />
248: <hr />
249: $lt{'exmpl'}
250:
251: <h3>$lt{'jsmath'}</h3>
252: <p>
1.67 albertel 253: $jsMath_start
1.148 bisitz 254: <script type="text/javascript" language="JavaScript">
1.54 albertel 255: if (jsMath.nofonts == 1) {
256: document.writeln
1.123 bisitz 257: ('<div style="padding: 10; border-style: solid; border-width:3;'
1.54 albertel 258: +' border-color: #DD0000; background-color: #FFF8F8; width: 75%; text-align: left">'
259: +'<small><font color="#AA0000"><b>Warning:</b> '
260: +'It looks like you don\\\'t have the TeX math fonts installed. '
261: +'The jsMath example on this page may not look right without them. '
262: +'The <a href="http://www.math.union.edu/locate/jsMath/" target="_blank"> '
263: +'jsMath Home Page</a> has information on how to download the '
264: +'needed fonts. In the meantime, jsMath will do the best it can '
265: +'with the fonts you have, but it may not be pretty and some equations '
266: +'may not be rendered correctly. '
1.123 bisitz 267: +'</font></small></div>');
1.54 albertel 268: }
269: </script>
1.122 www 270: <iframe src="/res/adm/pages/math_example.tex?inhibitmenu=yes&texengine=jsMath" width="400" height="120"></iframe>
1.123 bisitz 271: </p>
1.54 albertel 272:
1.123 bisitz 273: <h3>$lt{'mimetex'}</h3>
274: <p>
275: <iframe src="/res/adm/pages/math_example.tex?inhibitmenu=yes&texengine=mimetex" width="400" height="100"></iframe>
1.67 albertel 276: </p>
1.123 bisitz 277:
278: <h3>$lt{'tth'}</h3>
279: <p>
280: <iframe src="/res/adm/pages/math_example.tex?inhibitmenu=yes&texengine=tth" width="400" height="200"></iframe>
1.67 albertel 281: </p>
1.54 albertel 282: ENDLSCREEN
1.59 albertel 283: if ($env{'environment.texengine'} ne 'jsMath') {
1.148 bisitz 284: $r->print('<script type="text/javascript" language="JavaScript">jsMath.Process()</script>');
1.55 albertel 285: }
1.54 albertel 286: }
287:
288:
289: sub verify_and_change_texengine {
290: my $r = shift;
1.59 albertel 291: my $user = $env{'user.name'};
292: my $domain = $env{'user.domain'};
1.54 albertel 293: # Screenname
1.59 albertel 294: my $newtexengine = $env{'form.texengine'};
1.54 albertel 295: $newtexengine=~s/[^\-\w]//g;
1.56 albertel 296: if ($newtexengine eq 'ttm') {
1.116 raeburn 297: &Apache::lonnet::appenv({'browser.mathml' => 1});
1.56 albertel 298: } else {
1.59 albertel 299: if ($env{'environment.texengine'} eq 'ttm') {
1.116 raeburn 300: &Apache::lonnet::appenv({'browser.mathml' => 0});
1.56 albertel 301: }
302: }
1.54 albertel 303: my $message='';
304: if ($newtexengine) {
305: &Apache::lonnet::put('environment',{'texengine' => $newtexengine});
1.116 raeburn 306: &Apache::lonnet::appenv({'environment.texengine' => $newtexengine});
1.110 bisitz 307: $message=&mt('Set new preferred math display to ').'<tt>"'.$newtexengine.'"</tt>.';
1.54 albertel 308: } else {
309: &Apache::lonnet::del('environment',['texengine']);
1.139 raeburn 310: &Apache::lonnet::delenv('environment.texengine');
1.110 bisitz 311: $message=&mt('Reset preferred math display.');
1.54 albertel 312: }
1.56 albertel 313:
314:
1.126 droeschl 315: # $r->print(<<ENDVCSCREEN);
316: #$message
317: #ENDVCSCREEN
318: print_main_menu($r, $message);
1.54 albertel 319: }
320:
321: ################################################################
1.50 albertel 322: # Roles Page Preference Change Subroutines #
323: ################################################################
324: sub rolesprefchanger {
325: my $r = shift;
1.96 albertel 326: my $role = ($env{'user.adv'} ? 'Role' : 'Course');
327: my $lc_role = ($env{'user.adv'} ? 'role' : 'course');
1.59 albertel 328: my $user = $env{'user.name'};
329: my $domain = $env{'user.domain'};
1.50 albertel 330: my %userenv = &Apache::lonnet::get
331: ('environment',['recentroles','recentrolesn']);
1.126 droeschl 332: Apache::lonhtmlcommon::add_breadcrumb(
333: { href => '/adm/preferences?action=changerolespref',
334: text => 'Change '.$role.' Page Pref'});
1.147 schafran 335: $r->print(Apache::loncommon::start_page('Content Display Settings'));
1.126 droeschl 336: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change '.$role.' Page Pref'));
1.50 albertel 337: my $hotlist_flag=$userenv{'recentroles'};
338: my $hotlist_n=$userenv{'recentrolesn'};
339: my $checked;
340: if ($hotlist_flag) {
341: $checked = 'checked="checked"';
342: }
343:
344: if (!$hotlist_n) { $hotlist_n=3; }
345: my $options;
346: for (my $i=1; $i<10; $i++) {
347: my $select;
348: if ($hotlist_n == $i) { $select = 'selected="selected"'; }
349: $options .= "<option $select>$i</option>\n";
350: }
351:
1.89 albertel 352: # Get list of recent roles and display with checkbox in front
353: my $roles_check_list = '';
354: my $role_key='';
355: if ($env{'environment.recentroles'}) {
356: my %recent_roles =
357: &Apache::lonhtmlcommon::get_recent('roles',$env{'environment.recentrolesn'});
1.91 albertel 358: my %frozen_roles =
359: &Apache::lonhtmlcommon::get_recent_frozen('roles',$env{'environment.recentrolesn'});
1.89 albertel 360:
1.93 albertel 361: my %role_text = &rolespref_get_role_text([keys(%recent_roles)]);
1.92 albertel 362: my @sorted_roles = sort {$role_text{$a} cmp $role_text{$b}} keys(%role_text);
363:
1.89 albertel 364: $roles_check_list .=
365: &Apache::loncommon::start_data_table().
366: &Apache::loncommon::start_data_table_header_row().
1.96 albertel 367: "<th>".&mt('Freeze '.$role)."</th>".
368: "<th>".&mt($role)."</td>".
1.89 albertel 369: &Apache::loncommon::end_data_table_header_row().
370: "\n";
371: my $count;
1.92 albertel 372: foreach $role_key (@sorted_roles) {
1.89 albertel 373: my $checked = "";
374: my $value = $recent_roles{$role_key};
1.91 albertel 375: if ($frozen_roles{$role_key}) {
1.89 albertel 376: $checked = "checked=\"checked\"";
377: }
378: $count++;
379: $roles_check_list .=
380: &Apache::loncommon::start_data_table_row().
381: '<td class="LC_table_cell_checkbox">'.
382: "<input type=\"checkbox\" $checked name=\"freezeroles\"".
383: " id=\"freezeroles$count\" value=\"$role_key\" /></td>".
384: "<td><label for=\"freezeroles$count\">".
1.92 albertel 385: "$role_text{$role_key}</label></td>".
1.89 albertel 386: &Apache::loncommon::end_data_table_row(). "\n";
387: }
388: $roles_check_list .= "</table>\n";
389: }
390:
391: $r->print('
1.96 albertel 392: <p>'.&mt('Some LON-CAPA users have a long list of '.$lc_role.'s. The Recent '.$role.'s Hotlist feature keeps track of the last N '.$lc_role.'s which have been visited and places a table of these at the top of the '.$lc_role.'s page. People with very few '.$lc_role.'s should leave this feature disabled.').'
1.50 albertel 393: </p>
1.89 albertel 394: <form name="prefs" action="/adm/preferences" method="POST">
1.50 albertel 395: <input type="hidden" name="action" value="verify_and_change_rolespref" />
1.96 albertel 396: <br /><label>'.&mt('Enable Recent '.$role.'s Hotlist:').'
1.89 albertel 397: <input type="checkbox" '.$checked.' name="recentroles" value="true" /></label>
1.96 albertel 398: <br />'.&mt('Number of '.$role.'s in Hotlist:').'
1.50 albertel 399: <select name="recentrolesn" size="1">
1.89 albertel 400: '.$options.'
1.50 albertel 401: </select>
1.96 albertel 402: <p>'.&mt('This list below can be used to <q>freeze</q> '.$lc_role.'s on your screen. Those marked as frozen will not be removed from the list, even if they have not been used recently.').'
1.89 albertel 403: </p>
404: '.$roles_check_list.'
1.50 albertel 405: <br />
1.136 schafran 406: <input type="submit" value="'.&mt('Save').'" />
1.89 albertel 407: </form>');
1.50 albertel 408: }
409:
1.92 albertel 410: sub rolespref_get_role_text {
411: # Get a line of text for each role
412: my ($roles) = @_;
413: my %roletext = ();
414:
415: foreach my $item (@$roles) {
416: # get course information
417: my ($role,$rest) = split(/\./, $item);
1.93 albertel 418: my $trole = "";
419: $trole = &Apache::lonnet::plaintext($role);
1.92 albertel 420: my ($tdomain,$other,$tsection)= split(/\//,Apache::lonnet::declutter($rest));
421: my $tother = '-';
1.93 albertel 422: if ($role =~ /^(cc|st|in|ta|ep|cr)/ ) {
1.92 albertel 423: my %newhash=&Apache::lonnet::coursedescription($tdomain."_".$other);
424: $tother = " - ".$newhash{'description'};
425: } elsif ($role =~ /dc/) {
426: $tother = "";
427: } else {
428: $tother = " - $other";
429: }
430:
431: my $section="";
432: if ($tsection) {
433: $section = " - Section/Group: $tsection";
434: }
435: $roletext{$item} = $tdomain." - ".$trole.$tother.$section;
436: }
437: return %roletext;
438: }
439:
1.50 albertel 440: sub verify_and_change_rolespref {
441: my $r = shift;
1.96 albertel 442: my $role = ($env{'user.adv'} ? 'Role' : 'Course');
1.59 albertel 443: my $user = $env{'user.name'};
444: my $domain = $env{'user.domain'};
1.50 albertel 445: # Recent Roles Hotlist Flag
1.59 albertel 446: my $hotlist_flag = $env{'form.recentroles'};
447: my $hotlist_n = $env{'form.recentrolesn'};
1.89 albertel 448: my $message='<hr />';
1.50 albertel 449: if ($hotlist_flag) {
450: &Apache::lonnet::put('environment',{'recentroles' => $hotlist_flag});
1.116 raeburn 451: &Apache::lonnet::appenv({'environment.recentroles' => $hotlist_flag});
1.96 albertel 452: $message=&mt('Recent '.$role.'s Hotlist is Enabled');
1.50 albertel 453: } else {
454: &Apache::lonnet::del('environment',['recentroles']);
1.139 raeburn 455: &Apache::lonnet::delenv('environment.recentroles');
1.96 albertel 456: $message=&mt('Recent '.$role.'s Hotlist is Disabled');
1.50 albertel 457: }
458: if ($hotlist_n) {
459: &Apache::lonnet::put('environment',{'recentrolesn' => $hotlist_n});
1.116 raeburn 460: &Apache::lonnet::appenv({'environment.recentrolesn' => $hotlist_n});
1.50 albertel 461: if ($hotlist_flag) {
1.90 albertel 462: $message.="<br />".
1.96 albertel 463: &mt('Display [_1] Most Recent '.$role.'s',$hotlist_n)."\n";
1.89 albertel 464: }
465: }
466:
467: # Get list of froze roles and list of recent roles
468: my @freeze_list = &Apache::loncommon::get_env_multiple('form.freezeroles');
469: my %freeze = ();
1.92 albertel 470: my %roletext = ();
471:
1.89 albertel 472: foreach my $key (@freeze_list) {
1.91 albertel 473: $freeze{$key}='1';
1.89 albertel 474: }
1.92 albertel 475:
1.89 albertel 476: my %recent_roles =
477: &Apache::lonhtmlcommon::get_recent('roles',$env{'environment.recentrolesn'});
1.91 albertel 478: my %frozen_roles =
479: &Apache::lonhtmlcommon::get_recent_frozen('roles',$env{'environment.recentrolesn'});
1.92 albertel 480: my %role_text = &rolespref_get_role_text([keys(%recent_roles)]);
1.89 albertel 481:
482: # Unset any roles that were previously frozen but aren't in list
483: foreach my $role_key (sort(keys(%recent_roles))) {
1.91 albertel 484: if (($frozen_roles{$role_key}) && (!exists($freeze{$role_key}))) {
1.96 albertel 485: $message .= "<br />".&mt('Unfreezing '.$role.': [_1]',$role_text{$role_key})."\n";
1.91 albertel 486: &Apache::lonhtmlcommon::store_recent('roles',$role_key,' ',0);
1.89 albertel 487: }
488: }
489:
490: # Freeze selected roles
491: foreach my $role_key (@freeze_list) {
1.91 albertel 492: if (!$frozen_roles{$role_key}) {
1.96 albertel 493: $message .= "<br />".&mt('Freezing '.$role.': [_1]',$role_text{$role_key})."\n";
1.89 albertel 494: &Apache::lonhtmlcommon::store_recent('roles',
1.91 albertel 495: $role_key,' ',1);
1.50 albertel 496: }
497: }
1.89 albertel 498: $message .= "<hr /><br />\n";
1.50 albertel 499:
1.126 droeschl 500: # $r->print(<<ENDRPSCREEN);
501: #$message
502: #ENDRPSCREEN
503: print_main_menu($r, $message);
1.50 albertel 504: }
505:
506:
1.28 www 507:
508: ################################################################
1.9 matthew 509: # Anonymous Discussion Name Change Subroutines #
510: ################################################################
1.5 www 511: sub screennamechanger {
512: my $r = shift;
1.59 albertel 513: my $user = $env{'user.name'};
514: my $domain = $env{'user.domain'};
1.14 www 515: my %userenv = &Apache::lonnet::get
516: ('environment',['screenname','nickname']);
1.6 www 517: my $screenname=$userenv{'screenname'};
1.14 www 518: my $nickname=$userenv{'nickname'};
1.126 droeschl 519: Apache::lonhtmlcommon::add_breadcrumb(
520: { href => '/adm/preferences?action=changescreenname',
521: text => 'Change Screen Name'});
1.147 schafran 522: $r->print(Apache::loncommon::start_page('Personal Data'));
1.126 droeschl 523: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Screen Name'));
1.133 bisitz 524: $r->print('<p>'
525: .&mt('Change the name that is displayed in your posts.')
526: .'</p>'
527: );
528: $r->print('<form name="prefs" action="/adm/preferences" method="post">'
529: .'<input type="hidden" name="action" value="verify_and_change_screenname" />'
530: .&Apache::lonhtmlcommon::start_pick_box()
531: .&Apache::lonhtmlcommon::row_title(&mt('New screenname (shown if you post anonymously)'))
532: .'<input type="text" size="20" value="'.$screenname.'" name="screenname" />'
533: .&Apache::lonhtmlcommon::row_closure()
534: .&Apache::lonhtmlcommon::row_title(&mt('New nickname (shown if you post non-anonymously)'))
535: .'<input type="text" size="20" value="'.$nickname.'" name="nickname" />'
536: .&Apache::lonhtmlcommon::row_closure()
537: .&Apache::lonhtmlcommon::row_title()
538: .'<input type="submit" value="'.&mt('Save').'" />'
539: .&Apache::lonhtmlcommon::row_closure(1)
540: .&Apache::lonhtmlcommon::end_pick_box()
541: .'</form>'
542: );
1.5 www 543: }
1.6 www 544:
545: sub verify_and_change_screenname {
546: my $r = shift;
1.59 albertel 547: my $user = $env{'user.name'};
548: my $domain = $env{'user.domain'};
1.14 www 549: # Screenname
1.59 albertel 550: my $newscreen = $env{'form.screenname'};
1.14 www 551: $newscreen=~s/[^ \w]//g;
1.6 www 552: my $message='';
553: if ($newscreen) {
1.7 www 554: &Apache::lonnet::put('environment',{'screenname' => $newscreen});
1.116 raeburn 555: &Apache::lonnet::appenv({'environment.screenname' => $newscreen});
1.110 bisitz 556: $message=&mt('Set new screenname to ').'<tt>"'.$newscreen.'."</tt>.';
1.6 www 557: } else {
558: &Apache::lonnet::del('environment',['screenname']);
1.139 raeburn 559: &Apache::lonnet::delenv('environment.screenname');
1.110 bisitz 560: $message=&mt('Reset screenname.');
1.6 www 561: }
1.14 www 562: # Nickname
563: $message.='<br />';
1.59 albertel 564: $newscreen = $env{'form.nickname'};
1.14 www 565: $newscreen=~s/[^ \w]//g;
566: if ($newscreen) {
567: &Apache::lonnet::put('environment',{'nickname' => $newscreen});
1.116 raeburn 568: &Apache::lonnet::appenv({'environment.nickname' => $newscreen});
1.110 bisitz 569: $message.=&mt('Set new nickname to ').'<tt>"'.$newscreen.'"</tt>.';
1.14 www 570: } else {
571: &Apache::lonnet::del('environment',['nickname']);
1.139 raeburn 572: &Apache::lonnet::delenv('environment.nickname');
1.110 bisitz 573: $message.=&mt('Reset nickname.');
1.14 www 574: }
1.68 www 575: &Apache::lonnet::devalidate_cache_new('namescache',$user.':'.$domain);
1.126 droeschl 576: # $r->print(<<ENDVCSCREEN);
577: #$message
578: #ENDVCSCREEN
579: print_main_menu($r, $message);
1.20 www 580: }
581:
582: ################################################################
1.98 www 583: # Icon Subroutines #
584: ################################################################
585: sub iconchanger {
586: my $r = shift;
1.126 droeschl 587: Apache::lonhtmlcommon::add_breadcrumb(
588: { href => '/adm/preferences?action=changeicons',
589: text => 'Change Main Menu'});
1.147 schafran 590: $r->print(Apache::loncommon::start_page('Page Display Settings'));
1.126 droeschl 591: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Main Menu'));
592:
1.98 www 593: my $user = $env{'user.name'};
594: my $domain = $env{'user.domain'};
595: my %userenv = &Apache::lonnet::get
596: ('environment',['icons']);
597: my $iconic='checked="checked"';
598: my $classic='';
1.100 www 599: my $onlyicon='';
1.98 www 600: if ($userenv{'icons'} eq 'classic') {
601: $classic='checked="checked"';
602: $iconic='';
603: }
1.100 www 604: if ($userenv{'icons'} eq 'iconsonly') {
605: $onlyicon='checked="checked"';
606: $iconic='';
607: }
608: my $useicons=&mt('Use icons and text');
609: my $usebuttons=&mt('Use buttons and text');
610: my $useicononly=&mt('Use icons only');
1.136 schafran 611: my $change=&mt('Save');
1.98 www 612: $r->print(<<ENDSCREEN);
613: <form name="prefs" action="/adm/preferences" method="post">
614: <input type="hidden" name="action" value="verify_and_change_icons" />
615: <label><input type="radio" name="menumode" value="iconic" $iconic /> $useicons</label><br />
616: <label><input type="radio" name="menumode" value="classic" $classic /> $usebuttons</label><br />
1.100 www 617: <label><input type="radio" name="menumode" value="iconsonly" $onlyicon /> $useicononly</label><br />
1.98 www 618: <input type="submit" value="$change" />
619: </form>
620: ENDSCREEN
621: }
622:
623: sub verify_and_change_icons {
624: my $r = shift;
625: my $user = $env{'user.name'};
626: my $domain = $env{'user.domain'};
627: my $newicons = $env{'form.menumode'};
628:
629: &Apache::lonnet::put('environment',{'icons' => $newicons});
1.116 raeburn 630: &Apache::lonnet::appenv({'environment.icons' => $newicons});
1.126 droeschl 631: # $r->print(&mt('Set menu mode to [_1].',$newicons));
632: print_main_menu($r, &mt('Set menu mode to [_1].',$newicons));
1.98 www 633: }
634:
635: ################################################################
1.105 www 636: # Clicker Subroutines #
637: ################################################################
638:
639: sub clickerchanger {
640: my $r = shift;
1.126 droeschl 641: Apache::lonhtmlcommon::add_breadcrumb(
642: { href => '/adm/preferences?action=changeclicker',
643: text => 'Register Clicker'});
1.147 schafran 644: $r->print(Apache::loncommon::start_page('Other'));
1.126 droeschl 645: $r->print(Apache::lonhtmlcommon::breadcrumbs('Register Clicker'));
1.105 www 646: my $user = $env{'user.name'};
647: my $domain = $env{'user.domain'};
648: my %userenv = &Apache::lonnet::get
649: ('environment',['clickers']);
650: my $clickers=$userenv{'clickers'};
651: $clickers=~s/\,/\n/gs;
652: my $text=&mt('Enter response device ("clicker") numbers');
1.151 ! bisitz 653: my $change=&mt('Save');
1.114 bisitz 654: my $helplink=&Apache::loncommon::help_open_topic('Clicker_Registration',&mt('Locating your clicker ID'));
1.105 www 655: $r->print(<<ENDSCREEN);
656: <form name="prefs" action="/adm/preferences" method="post">
657: <input type="hidden" name="action" value="verify_and_change_clicker" />
1.151 ! bisitz 658: <label>$helplink<br /><br />$text<br />
1.108 www 659: <textarea name="clickers" rows="5" cols="20">$clickers</textarea>
1.105 www 660: </label>
1.151 ! bisitz 661: <br />
1.105 www 662: <input type="submit" value="$change" />
663: </form>
664: ENDSCREEN
665: }
666:
667: sub verify_and_change_clicker {
668: my $r = shift;
669: my $user = $env{'user.name'};
670: my $domain = $env{'user.domain'};
671: my $newclickers = $env{'form.clickers'};
1.108 www 672: $newclickers=~s/[^\w\:\-]+/\,/gs;
1.105 www 673: $newclickers=~tr/a-z/A-Z/;
1.108 www 674: $newclickers=~s/[\:\-]+/\-/g;
675: $newclickers=~s/\,+/\,/g;
1.105 www 676: $newclickers=~s/^\,//;
677: $newclickers=~s/\,$//;
678: &Apache::lonnet::put('environment',{'clickers' => $newclickers});
1.116 raeburn 679: &Apache::lonnet::appenv({'environment.clickers' => $newclickers});
1.126 droeschl 680: # $r->print(&mt('Registering clickers: [_1]',$newclickers));
681: print_main_menu($r, &mt('Registering clickers: [_1]',$newclickers));
1.105 www 682: }
683:
1.119 www 684: ################################################################
685: # Domcoord Access Subroutines #
686: ################################################################
687:
688: sub domcoordchanger {
689: my $r = shift;
1.126 droeschl 690: Apache::lonhtmlcommon::add_breadcrumb(
691: { href => '/adm/preferences?action=changedomcoord',
692: text => 'Restrict Domain Coordinator Access'});
693: $r->print(Apache::loncommon::start_page('Restrict Domain Coordinator Access'));
694: $r->print(Apache::lonhtmlcommon::breadcrumbs('Restrict Domain Coordinator Access'));
1.119 www 695: my $user = $env{'user.name'};
696: my $domain = $env{'user.domain'};
697: my %userenv = &Apache::lonnet::get
1.120 www 698: ('environment',['domcoord.author']);
1.119 www 699: my $constchecked='';
700: if ($userenv{'domcoord.author'} eq 'blocked') {
701: $constchecked='checked="checked"';
702: }
1.120 www 703: my $text=&mt('By default, the Domain Coordinator can enter your construction space.');
1.119 www 704: my $construction=&mt('Block access to construction space');
1.136 schafran 705: my $change=&mt('Save');
1.119 www 706: $r->print(<<ENDSCREEN);
707: <form name="prefs" action="/adm/preferences" method="post">
708: <input type="hidden" name="action" value="verify_and_change_domcoord" />
709: $text<br />
710: <label><input type="checkbox" name="construction" $constchecked />$construction</label><br />
711: <input type="submit" value="$change" />
712: </form>
713: ENDSCREEN
714: }
715:
716: sub verify_and_change_domcoord {
717: my $r = shift;
718: my $user = $env{'user.name'};
719: my $domain = $env{'user.domain'};
1.120 www 720: my %domcoord=('domcoord.author' => '');
1.119 www 721: if ($env{'form.construction'}) { $domcoord{'domcoord.author'}='blocked'; }
722: &Apache::lonnet::put('environment',\%domcoord);
1.120 www 723: &Apache::lonnet::appenv({'environment.domcoord.author' => $domcoord{'domcoord.author'}});
1.126 droeschl 724: # $r->print(&mt('Registering Domain Coordinator access restrictions.'));
725: print_main_menu($r, &mt('Registering Domain Coordinator access restrictions.'));
1.119 www 726: }
727:
1.118 www 728: #################################################################
729: ## Lock Subroutines #
730: #################################################################
731:
732: sub lockwarning {
733: my $r = shift;
734: my $title=&mt('Action locked');
735: my $texttop=&mt('LON-CAPA is currently performing the following actions:');
736: my $textbottom=&mt('Changing roles or logging out may result in data corruption.');
737: my ($num,%which)=&Apache::lonnet::get_locks();
738: my $which='';
739: foreach my $id (keys %which) {
740: $which.='<li>'.$which{$id}.'</li>';
741: }
742: my $change=&mt('Override');
743: $r->print(<<ENDSCREEN);
744: <form name="prefs" action="/adm/preferences" method="post">
745: <input type="hidden" name="action" value="verify_and_change_locks" />
746: <h1>$title</h1>
747: $texttop
748: <ul>
749: $which
750: </ul>
751: $textbottom
752: <input type="submit" value="$change" />
753: </form>
754: ENDSCREEN
755: }
756:
757: sub verify_and_change_lockwarning {
758: my $r = shift;
759: &Apache::lonnet::remove_all_locks();
760: $r->print(&mt('Cleared locks.'));
761: }
762:
763:
1.105 www 764: ################################################################
1.20 www 765: # Message Forward #
766: ################################################################
767:
768: sub msgforwardchanger {
1.102 raeburn 769: my ($r,$message) = @_;
1.59 albertel 770: my $user = $env{'user.name'};
771: my $domain = $env{'user.domain'};
1.102 raeburn 772: my %userenv = &Apache::lonnet::get('environment',['msgforward','notification','critnotification','notifywithhtml']);
1.20 www 773: my $msgforward=$userenv{'msgforward'};
1.102 raeburn 774: my %lt = &Apache::lonlocal::texthash(
775: all => 'All',
776: crit => 'Critical only',
777: reg => 'Non-critical only',
778: foad => 'Forwarding Address(es)',
1.113 raeburn 779: noti => 'Notification E-mail Address(es)',
1.110 bisitz 780: foad_exmpl => 'e.g. <tt>userA:domain1,userB:domain2,...</tt>',
1.130 schafran 781: mnot => 'E-mail Address(es) which should be notified about new LON-CAPA messages',
782: # old: 'Message Notification Email Address(es)',
1.110 bisitz 783: mnot_exmpl => 'e.g. <tt>joe@doe.com</tt>',
1.136 schafran 784: chg => 'Save',
1.104 raeburn 785: email => 'The e-mail address entered in row ',
1.102 raeburn 786: notv => 'is not a valid e-mail address',
1.103 raeburn 787: toen => "To enter multiple addresses, enter one address at a time, click 'Change' and then add the next one",
1.136 schafran 788: prme => 'Back',
1.102 raeburn 789: );
1.126 droeschl 790: Apache::lonhtmlcommon::add_breadcrumb(
791: { href => '/adm/preferences?action=changemsgforward',
792: text => 'Change Message Forwarding/Notification'});
1.147 schafran 793: $r->print(Apache::loncommon::start_page('Message Management'));
1.126 droeschl 794: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Message Forwarding/Notification'));
1.113 raeburn 795: my $forwardingHelp = &Apache::loncommon::help_open_topic("Prefs_Forwarding");
796: my $notificationHelp = &Apache::loncommon::help_open_topic("Prefs_Notification");
797: my $criticalMessageHelp = &Apache::loncommon::help_open_topic("Course_Critical_Message");
1.102 raeburn 798: my @allow_html = split(/,/,$userenv{'notifywithhtml'});
799: my %allnot = &get_notifications(\%userenv);
800: my $validatescript = &Apache::lonhtmlcommon::javascript_valid_email();
801: my $jscript = qq|
1.148 bisitz 802: <script type="text/javascript" language="JavaScript">
1.102 raeburn 803: function validate() {
804: for (var i=0; i<document.prefs.numnotify.value; i++) {
1.104 raeburn 805: var checkaddress = 0;
1.102 raeburn 806: var addr = document.prefs.elements['address_'+i].value;
1.104 raeburn 807: var rownum = i+1;
1.102 raeburn 808: if (i < document.prefs.numnotify.value-1) {
1.104 raeburn 809: if (document.prefs.elements['modify_notify_'+i].checked) {
1.102 raeburn 810: checkaddress = 1;
1.104 raeburn 811: }
1.102 raeburn 812: } else {
813: if (document.prefs.elements['add_notify_'+i].checked == true) {
814: checkaddress = 1;
815: }
816: }
1.104 raeburn 817: if (checkaddress == 1) {
1.102 raeburn 818: var addr = document.prefs.elements['address_'+i].value;
819: if (validmail(document.prefs.elements['address_'+i]) == false) {
1.104 raeburn 820: var multimsg = '';
821: if (addr.indexOf(",") >= 0) {
822: multimsg = "\\n($lt{'toen'}).";
823: }
1.110 bisitz 824: alert("$lt{'email'} "+rownum+" ('"+addr+"') $lt{'notv'}."+multimsg);
1.102 raeburn 825: return;
826: }
827: }
828: }
829: document.prefs.submit();
830: }
1.104 raeburn 831:
832: function address_changes (adnum) {
833: if (!document.prefs.elements['del_notify_'+adnum].checked) {
834: document.prefs.elements['modify_notify_'+adnum].checked = true;
835: }
836: }
837:
838: function new_address(adnum) {
839: document.prefs.elements['add_notify_'+adnum].checked = true;
840: }
841:
842: function delete_address(adnum) {
843: if (document.prefs.elements['del_notify_'+adnum].checked) {
844: document.prefs.elements['modify_notify_'+adnum].checked = false;
845: }
846: }
847:
848: function modify_address(adnum) {
849: if (document.prefs.elements['modify_notify_'+adnum].checked) {
850: document.prefs.elements['del_notify_'+adnum].checked = false;
851: }
852: }
853:
1.102 raeburn 854: $validatescript
855: </script>
856: |;
1.20 www 857: $r->print(<<ENDMSG);
1.102 raeburn 858: $jscript
859: $message
1.113 raeburn 860: <h3>$lt{'foad'} $forwardingHelp</h3>
1.88 albertel 861: <form name="prefs" action="/adm/preferences" method="post">
1.20 www 862: <input type="hidden" name="action" value="verify_and_change_msgforward" />
1.110 bisitz 863: $lt{'foad'} ($lt{'foad_exmpl'}):
1.113 raeburn 864: <input type="text" size="40" value="$msgforward" name="msgforward" /><br />
865: <h3>$lt{'noti'} $notificationHelp</h3>
1.110 bisitz 866: $lt{'mnot'} ($lt{'mnot_exmpl'}):<br />
1.102 raeburn 867: ENDMSG
868: my @sortforwards = sort (keys(%allnot));
869: my $output = &Apache::loncommon::start_data_table().
870: &Apache::loncommon::start_data_table_header_row().
1.104 raeburn 871: '<th> </th>'.
1.102 raeburn 872: '<th>'.&mt('Action').'</th>'.
873: '<th>'.&mt('Notification address').'</th><th>'.
1.113 raeburn 874: &mt('Types of message for which notification is sent').
875: $criticalMessageHelp.'</th><th>'.
1.104 raeburn 876: &mt('Excerpt retains HTML tags in message').'</th>'.
1.102 raeburn 877: &Apache::loncommon::end_data_table_header_row();
878: my $num = 0;
1.104 raeburn 879: my $counter = 1;
1.102 raeburn 880: foreach my $item (@sortforwards) {
881: $output .= &Apache::loncommon::start_data_table_row().
1.104 raeburn 882: '<td><b>'.$counter.'</b></td>'.
883: '<td><span class="LC_nobreak"><label>'.
884: '<input type="checkbox" name="modify_notify_'.
885: $num.'" onclick="javscript:modify_address('."'$num'".')" />'.
886: &mt('Modify').'</label></span> '.
887: '<span class="LC_nobreak"><label>'.
888: '<input type="checkbox" name="del_notify_'.$num.
889: '" onclick="javscript:delete_address('."'$num'".')" />'.
890: &mt('Delete').'</label></span></td>'.
1.102 raeburn 891: '<td><input type="text" value="'.$item.'" name="address_'.
1.104 raeburn 892: $num.'" onFocus="javascript:address_changes('."'$num'".
893: ')" /></td><td>';
1.102 raeburn 894: my %chk;
895: if (defined($allnot{$item}{'crit'})) {
896: if (defined($allnot{$item}{'reg'})) {
897: $chk{'all'} = 'checked="checked" ';
898: } else {
899: $chk{'crit'} = 'checked="checked" ';
900: }
901: } else {
902: $chk{'reg'} = 'checked="checked" ';
903: }
904: foreach my $type ('all','crit','reg') {
905: $output .= '<span class="LC_nobreak"><label>'.
906: '<input type="radio" name="notify_type_'.$num.
1.104 raeburn 907: '" value="'.$type.'" '.$chk{$type}.
908: ' onchange="javascript:address_changes('."'$num'".')" />'.
909: $lt{$type}.'</label></span> ';
1.102 raeburn 910: }
911: my $htmlon = '';
912: my $htmloff = '';
913: if (grep/^\Q$item\E/,@allow_html) {
914: $htmlon = 'checked="checked" ';
915: } else {
916: $htmloff = 'checked="checked" ';
917: }
918: $output .= '</td><td><label><input type="radio" name="html_'.$num.
1.104 raeburn 919: '" value="1" '.$htmlon.
920: ' onchange="javascript:address_changes('."'$num'".')" />'.
921: &mt('Yes').'</label> '.
1.102 raeburn 922: '<label><input type="radio" name="html_'.$num.'" value="0" '.
1.104 raeburn 923: $htmloff. ' onchange="javascript:address_changes('."'$num'".
924: ')" />'.
925: &mt('No').'</label></td>'.
1.102 raeburn 926: &Apache::loncommon::end_data_table_row();
927: $num ++;
1.104 raeburn 928: $counter ++;
1.102 raeburn 929: }
930: my %defchk = (
931: all => 'checked="checked" ',
932: crit => '',
933: reg => '',
934: );
935: $output .= &Apache::loncommon::start_data_table_row().
1.104 raeburn 936: '<td><b>'.$counter.'</b></td>'.
937: '<td><span class="LC_nobreak"><label>'.
938: '<input type="checkbox" name="add_notify_'.$num.
939: '" value="1" />'.&mt('Add new address').'</label></span></td>'.
1.102 raeburn 940: '<td><input type="text" value="" name="address_'.$num.
1.104 raeburn 941: '" onFocus="javascript:new_address('."'$num'".')" /></td><td>';
1.102 raeburn 942: foreach my $type ('all','crit','reg') {
943: $output .= '<span class="LC_nobreak"><label>'.
944: '<input type="radio" name="notify_type_'.$num.
945: '" value="'.$type.'" '.$defchk{$type}.'/>'.
946: $lt{$type}.'</label></span> ';
947: }
948: $output .= '</td><td><label><input type="radio" name="html_'.$num.
949: '" value="1" />'.&mt('Yes').'</label> '.
950: '<label><input type="radio" name="html_'.$num.'" value="0" '.
951: ' checked="checked" />'.
952: &mt('No').'</label></td>'.
953: &Apache::loncommon::end_data_table_row().
954: &Apache::loncommon::end_data_table();
955: $num ++;
956: $r->print($output);
957: $r->print(qq|
1.113 raeburn 958: <br /><hr />
1.102 raeburn 959: <input type="hidden" name="numnotify" value="$num" />
1.136 schafran 960: <input type="button" value="$lt{'prme'}" onclick="location.href='/adm/preferences'" />
1.102 raeburn 961: <input type="button" value="$lt{'chg'}" onclick="javascript:validate()" />
1.20 www 962: </form>
1.102 raeburn 963: |);
964:
965: }
966:
967: sub get_notifications {
968: my ($userenv) = @_;
969: my %allnot;
970: my @critnot = split(/,/,$userenv->{'critnotification'});
971: my @regnot = split(/,/,$userenv->{'notification'});
972: foreach my $item (@critnot) {
973: $allnot{$item}{crit} = 1;
974: }
975: foreach my $item (@regnot) {
976: $allnot{$item}{reg} = 1;
977: }
978: return %allnot;
1.20 www 979: }
980:
981: sub verify_and_change_msgforward {
982: my $r = shift;
1.59 albertel 983: my $user = $env{'user.name'};
984: my $domain = $env{'user.domain'};
1.20 www 985: my $newscreen = '';
986: my $message='';
1.59 albertel 987: foreach (split(/\,/,$env{'form.msgforward'})) {
1.20 www 988: my ($msuser,$msdomain)=split(/[\@\:]/,$_);
1.95 albertel 989: $msuser = &LONCAPA::clean_username($msuser);
990: $msdomain = &LONCAPA::clean_domain($msdomain);
1.20 www 991: if (($msuser) && ($msdomain)) {
992: if (&Apache::lonnet::homeserver($msuser,$msdomain) ne 'no_host') {
993: $newscreen.=$msuser.':'.$msdomain.',';
994: } else {
1.110 bisitz 995: $message.= &mt('No such user: ').'<tt>'.$msuser.':'.$msdomain.'</tt><br>';
1.20 www 996: }
997: }
998: }
999: $newscreen=~s/\,$//;
1000: if ($newscreen) {
1001: &Apache::lonnet::put('environment',{'msgforward' => $newscreen});
1.116 raeburn 1002: &Apache::lonnet::appenv({'environment.msgforward' => $newscreen});
1.110 bisitz 1003: $message .= &mt('Set message forwarding to ').'<tt>"'.$newscreen.'"</tt>.'
1004: .'<br />';
1.20 www 1005: } else {
1006: &Apache::lonnet::del('environment',['msgforward']);
1.139 raeburn 1007: &Apache::lonnet::delenv('environment.msgforward');
1.102 raeburn 1008: $message.= &mt("Set message forwarding to 'off'.").'<br />';
1.20 www 1009: }
1.102 raeburn 1010: my $critnotification;
1011: my $notification;
1012: my $notify_with_html;
1013: my $lastnotify = $env{'form.numnotify'}-1;
1.104 raeburn 1014: my $totaladdresses = 0;
1.102 raeburn 1015: for (my $i=0; $i<$env{'form.numnotify'}; $i++) {
1016: if ((!defined($env{'form.del_notify_'.$i})) &&
1.104 raeburn 1017: ((($i==$lastnotify) && ($env{'form.add_notify_'.$lastnotify} == 1)) ||
1.102 raeburn 1018: ($i<$lastnotify))) {
1019: if (defined($env{'form.address_'.$i})) {
1020: if ($env{'form.notify_type_'.$i} eq 'all') {
1021: $critnotification .= $env{'form.address_'.$i}.',';
1022: $notification .= $env{'form.address_'.$i}.',';
1023: } elsif ($env{'form.notify_type_'.$i} eq 'crit') {
1024: $critnotification .= $env{'form.address_'.$i}.',';
1025: } elsif ($env{'form.notify_type_'.$i} eq 'reg') {
1026: $notification .= $env{'form.address_'.$i}.',';
1027: }
1028: if ($env{'form.html_'.$i} eq '1') {
1029: $notify_with_html .= $env{'form.address_'.$i}.',';
1030: }
1.104 raeburn 1031: $totaladdresses ++;
1.102 raeburn 1032: }
1033: }
1034: }
1035: $critnotification =~ s/,$//;
1036: $critnotification=~s/\s//gs;
1037: $notification =~ s/,$//;
1.20 www 1038: $notification=~s/\s//gs;
1.102 raeburn 1039: $notify_with_html =~ s/,$//;
1040: $notify_with_html =~ s/\s//gs;
1.20 www 1041: if ($notification) {
1042: &Apache::lonnet::put('environment',{'notification' => $notification});
1.116 raeburn 1043: &Apache::lonnet::appenv({'environment.notification' => $notification});
1.110 bisitz 1044: $message.=&mt('Set non-critical message notification address(es) to ').'<tt>"'.$notification.'"</tt>.<br />';
1.20 www 1045: } else {
1046: &Apache::lonnet::del('environment',['notification']);
1.139 raeburn 1047: &Apache::lonnet::delenv('environment.notification');
1.110 bisitz 1048: $message.=&mt("Set non-critical message notification to 'off'.").'<br />';
1.20 www 1049: }
1050: if ($critnotification) {
1051: &Apache::lonnet::put('environment',{'critnotification' => $critnotification});
1.116 raeburn 1052: &Apache::lonnet::appenv({'environment.critnotification' => $critnotification});
1.110 bisitz 1053: $message.=&mt('Set critical message notification address(es) to ').'<tt>"'.$critnotification.'"</tt>.<br />';
1.20 www 1054: } else {
1055: &Apache::lonnet::del('environment',['critnotification']);
1.139 raeburn 1056: &Apache::lonnet::delenv('environment.critnotification');
1.110 bisitz 1057: $message.=&mt("Set critical message notification to 'off'.").'<br />';
1.102 raeburn 1058: }
1059: if ($critnotification || $notification) {
1060: if ($notify_with_html) {
1061: &Apache::lonnet::put('environment',{'notifywithhtml' => $notify_with_html});
1.116 raeburn 1062: &Apache::lonnet::appenv({'environment.notifywithhtml' => $notify_with_html});
1.110 bisitz 1063: $message.=&mt('Set address(es) to receive excerpts with html retained ').'<tt>"'.$notify_with_html.'"</tt>.';
1.102 raeburn 1064: } else {
1065: &Apache::lonnet::del('environment',['notifywithhtml']);
1.139 raeburn 1066: &Apache::lonnet::delenv('environment.notifywithhtml');
1.104 raeburn 1067: if ($totaladdresses == 1) {
1068: $message.=&mt("Set notification address to receive excerpts with html stripped.");
1069: } else {
1070: $message.=&mt("Set all notification addresses to receive excerpts with html stripped.");
1071: }
1.102 raeburn 1072: }
1073: } else {
1074: &Apache::lonnet::del('environment',['notifywithhtml']);
1.139 raeburn 1075: &Apache::lonnet::delenv('environment.notifywithhtml');
1.102 raeburn 1076: }
1077: if ($message) {
1078: $message .= '<br /><hr />';
1.20 www 1079: }
1.109 albertel 1080: &Apache::loncommon::flush_email_cache($user,$domain);
1.102 raeburn 1081: &msgforwardchanger($r,$message);
1.6 www 1082: }
1083:
1.12 www 1084: ################################################################
1.19 www 1085: # Colors #
1.12 www 1086: ################################################################
1087:
1.19 www 1088: sub colorschanger {
1.12 www 1089: my $r = shift;
1.126 droeschl 1090: Apache::lonhtmlcommon::add_breadcrumb(
1091: { href => '/adm/preferences?action=changecolors',
1092: text => 'Change Colors'});
1.147 schafran 1093: $r->print(Apache::loncommon::start_page('Page Display Settings'));
1.126 droeschl 1094: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Colors'));
1.19 www 1095: # figure out colors
1.80 albertel 1096: my $function=&Apache::loncommon::get_users_function();
1.19 www 1097: my $domain=&Apache::loncommon::determinedomain();
1098: my %colortypes=('pgbg' => 'Page Background',
1099: 'tabbg' => 'Header Background',
1100: 'sidebg'=> 'Header Border',
1101: 'font' => 'Font',
1102: 'link' => 'Un-Visited Link',
1103: 'vlink' => 'Visited Link',
1104: 'alink' => 'Active Link');
1.82 albertel 1105: my $start_data_table = &Apache::loncommon::start_data_table();
1.19 www 1106: my $chtable='';
1.22 matthew 1107: foreach my $item (sort(keys(%colortypes))) {
1.19 www 1108: my $curcol=&Apache::loncommon::designparm($function.'.'.$item,$domain);
1.82 albertel 1109: $chtable.=&Apache::loncommon::start_data_table_row().
1.83 albertel 1110: '<td>'.$colortypes{$item}.'</td><td style="background: '.$curcol.
1.19 www 1111: '"> </td><td><input name="'.$item.
1.21 www 1112: '" size="10" value="'.$curcol.
1113: '" /></td><td><a href="javascript:pjump('."'color_custom','".$colortypes{$item}.
1.19 www 1114: "','".$curcol."','"
1.82 albertel 1115: .$item."','parmform.pres','psub'".');">Select</a></td>'.
1.83 albertel 1116: &Apache::loncommon::end_data_table_row()."\n";
1.19 www 1117: }
1.82 albertel 1118: my $end_data_table = &Apache::loncommon::end_data_table();
1.23 matthew 1119: my $pjump_def = &Apache::lonhtmlcommon::pjump_javascript_definition();
1.138 schafran 1120: my $save = &mt('Save');
1121: my $rstall = &mt('Reset All');
1122: my $resetdefault = &mt('Reset All Colors to Default');
1.19 www 1123: $r->print(<<ENDCOL);
1.148 bisitz 1124: <script type="text/javascript" language="JavaScript">
1.19 www 1125:
1126: function pclose() {
1127: parmwin=window.open("/adm/rat/empty.html","LONCAPAparms",
1128: "height=350,width=350,scrollbars=no,menubar=no");
1129: parmwin.close();
1130: }
1131:
1.23 matthew 1132: $pjump_def
1.19 www 1133:
1134: function psub() {
1135: pclose();
1136: if (document.parmform.pres_marker.value!='') {
1.21 www 1137: if (document.parmform.pres_type.value!='') {
1.77 albertel 1138: eval('document.prefs.'+
1.21 www 1139: document.parmform.pres_marker.value+
1.19 www 1140: '.value=document.parmform.pres_value.value;');
1.21 www 1141: }
1.19 www 1142: } else {
1143: document.parmform.pres_value.value='';
1144: document.parmform.pres_marker.value='';
1145: }
1146: }
1147:
1148:
1149: </script>
1.21 www 1150: <form name="parmform">
1151: <input type="hidden" name="pres_marker" />
1152: <input type="hidden" name="pres_type" />
1153: <input type="hidden" name="pres_value" />
1154: </form>
1.88 albertel 1155: <form name="prefs" action="/adm/preferences" method="post">
1.19 www 1156: <input type="hidden" name="action" value="verify_and_change_colors" />
1.82 albertel 1157: $start_data_table
1.19 www 1158: $chtable
1.82 albertel 1159: $end_data_table
1.19 www 1160: </table>
1.138 schafran 1161: <input type="submit" value="$save" />
1162: <input type="submit" name="resetall" value="$rstall" title="$resetdefault" />
1.12 www 1163: </form>
1.19 www 1164: ENDCOL
1.12 www 1165: }
1166:
1.19 www 1167: sub verify_and_change_colors {
1.12 www 1168: my $r = shift;
1.19 www 1169: # figure out colors
1.80 albertel 1170: my $function=&Apache::loncommon::get_users_function();
1.19 www 1171: my $domain=&Apache::loncommon::determinedomain();
1172: my %colortypes=('pgbg' => 'Page Background',
1173: 'tabbg' => 'Header Background',
1174: 'sidebg'=> 'Header Border',
1175: 'font' => 'Font',
1176: 'link' => 'Un-Visited Link',
1177: 'vlink' => 'Visited Link',
1178: 'alink' => 'Active Link');
1179:
1.12 www 1180: my $message='';
1.21 www 1181: foreach my $item (keys %colortypes) {
1.59 albertel 1182: my $color=$env{'form.'.$item};
1.21 www 1183: my $entry='color.'.$function.'.'.$item;
1.59 albertel 1184: if (($color=~/^\#[0-9A-Fa-f]{6}$/) && (!$env{'form.resetall'})) {
1.21 www 1185: &Apache::lonnet::put('environment',{$entry => $color});
1.116 raeburn 1186: &Apache::lonnet::appenv({'environment.'.$entry => $color});
1.110 bisitz 1187: $message.=&mt('Set '.$colortypes{$item}.' to ').'<tt>"'.$color.'"</tt>.<br />';
1.21 www 1188: } else {
1189: &Apache::lonnet::del('environment',[$entry]);
1.138 schafran 1190: &Apache::lonnet::delenv('environment.'.$entry);
1.110 bisitz 1191: $message.=&mt('Reset '.$colortypes{$item}.'.').'<br />';
1.21 www 1192: }
1193: }
1.84 albertel 1194: my $now = time;
1195: &Apache::lonnet::put('environment',{'color.timestamp' => $now});
1.116 raeburn 1196: &Apache::lonnet::appenv({'environment.color.timestamp' => $now});
1.84 albertel 1197:
1.126 droeschl 1198: print_main_menu($r, $message);
1199: # $r->print(<<ENDVCCOL);
1200: #$message
1201: #<form name="client" action="/adm/preferences" method="post">
1202: #<input type="hidden" name="action" value="changecolors" />
1203: #</form>
1204: #ENDVCCOL
1.12 www 1205: }
1206:
1.4 matthew 1207: ######################################################
1208: # password handler subroutines #
1209: ######################################################
1.3 matthew 1210: sub passwordchanger {
1.94 raeburn 1211: my ($r,$errormessage,$caller,$mailtoken) = @_;
1.4 matthew 1212: # This function is a bit of a mess....
1.3 matthew 1213: # Passwords are encrypted using londes.js (DES encryption)
1.4 matthew 1214: $errormessage = ($errormessage || '');
1.94 raeburn 1215: my ($user,$domain,$currentpass,$defdom);
1.126 droeschl 1216: Apache::lonhtmlcommon::add_breadcrumb(
1217: { href => '/adm/preferences?action=changepass',
1218: text => 'Change Password'});
1.144 raeburn 1219: unless ($caller eq 'reset_by_email') {
1.147 schafran 1220: $r->print(Apache::loncommon::start_page('Personal Data'));
1.144 raeburn 1221: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Password'));
1222: }
1.94 raeburn 1223: if ((!defined($caller)) || ($caller eq 'preferences')) {
1224: $user = $env{'user.name'};
1225: $domain = $env{'user.domain'};
1226: if (!defined($caller)) {
1227: $caller = 'preferences';
1228: }
1229: } elsif ($caller eq 'reset_by_email') {
1230: $defdom = $r->dir_config('lonDefDomain');
1231: my %data = &Apache::lonnet::tmpget($mailtoken);
1232: if (keys(%data) == 0) {
1.110 bisitz 1233: $r->print(&mt('Sorry, the URL you provided to complete the reset of your password was invalid. Either the token included in the URL has been deleted or the URL you provided was invalid. Please submit a <a href="/adm/resetpw">new request</a> for a password reset, and follow the link to the new URL included in the e-mail that will be sent to you, to allow you to enter a new password.'));
1.94 raeburn 1234: return;
1235: }
1236: if (defined($data{time})) {
1237: if (time - $data{'time'} < 7200) {
1238: $user = $data{'username'};
1239: $domain = $data{'domain'};
1240: $currentpass = $data{'temppasswd'};
1241: } else {
1242: $r->print(&mt('Sorry, the token generated when you requested a password reset has expired.').'<br />');
1243: return;
1244: }
1245: } else {
1246: $r->print(&mt('Sorry, the URL generated when you requested reset of your password contained incomplete information.').'<br />');
1247: return;
1248: }
1249: } else {
1250: $r->print(&mt('Page requested in unexpected context').'<br />');
1251: return;
1252: }
1.3 matthew 1253: my $currentauth=&Apache::lonnet::queryauthenticate($user,$domain);
1254: # Check for authentication types that allow changing of the password.
1255: return if ($currentauth !~ /^(unix|internal):/);
1256: #
1257: # Generate keys
1258: my ($lkey_cpass ,$ukey_cpass ) = &des_keys();
1259: my ($lkey_npass1,$ukey_npass1) = &des_keys();
1260: my ($lkey_npass2,$ukey_npass2) = &des_keys();
1.4 matthew 1261: # Store the keys in the log files
1.3 matthew 1262: my $lonhost = $r->dir_config('lonHostID');
1263: my $logtoken=Apache::lonnet::reply('tmpput:'
1264: .$ukey_cpass . $lkey_cpass .'&'
1265: .$ukey_npass1 . $lkey_npass1.'&'
1266: .$ukey_npass2 . $lkey_npass2,
1267: $lonhost);
1.4 matthew 1268: # Hexify the keys for output as javascript variables
1.94 raeburn 1269: my %hexkey;
1270: $hexkey{'ukey_cpass'} = hex($ukey_cpass);
1271: $hexkey{'lkey_cpass'} = hex($lkey_cpass);
1272: $hexkey{'ukey_npass1'} = hex($ukey_npass1);
1273: $hexkey{'lkey_npass1'} = hex($lkey_npass1);
1274: $hexkey{'ukey_npass2'} = hex($ukey_npass2);
1275: $hexkey{'lkey_npass2'} = hex($lkey_npass2);
1.3 matthew 1276: # Output javascript to deal with passwords
1.4 matthew 1277: # Output DES javascript
1.3 matthew 1278: {
1279: my $include = $r->dir_config('lonIncludes');
1280: my $jsh=Apache::File->new($include."/londes.js");
1281: $r->print(<$jsh>);
1282: }
1.94 raeburn 1283: $r->print(&jscript_send($caller));
1.3 matthew 1284: $r->print(<<ENDFORM);
1.94 raeburn 1285: $errormessage
1286:
1287: <p>
1288: <!-- We separate the forms into 'server' and 'client' in order to
1289: ensure that unencrypted passwords will not be sent out by a
1290: crappy browser -->
1291: ENDFORM
1292: $r->print(&server_form($logtoken,$caller,$mailtoken));
1293: $r->print(&client_form($caller,\%hexkey,$currentpass,$defdom));
1294:
1295: #
1296: return;
1297: }
1298:
1299: sub jscript_send {
1300: my ($caller) = @_;
1301: my $output = qq|
1.148 bisitz 1302: <script type="text/javascript" language="JavaScript">
1.3 matthew 1303:
1304: function send() {
1305: uextkey=this.document.client.elements.ukey_cpass.value;
1306: lextkey=this.document.client.elements.lkey_cpass.value;
1307: initkeys();
1308:
1.52 raeburn 1309: this.document.pserver.elements.currentpass.value
1.3 matthew 1310: =crypted(this.document.client.elements.currentpass.value);
1311:
1312: uextkey=this.document.client.elements.ukey_npass1.value;
1313: lextkey=this.document.client.elements.lkey_npass1.value;
1314: initkeys();
1.52 raeburn 1315: this.document.pserver.elements.newpass_1.value
1.3 matthew 1316: =crypted(this.document.client.elements.newpass_1.value);
1317:
1318: uextkey=this.document.client.elements.ukey_npass2.value;
1319: lextkey=this.document.client.elements.lkey_npass2.value;
1320: initkeys();
1.52 raeburn 1321: this.document.pserver.elements.newpass_2.value
1.3 matthew 1322: =crypted(this.document.client.elements.newpass_2.value);
1.94 raeburn 1323: |;
1324: if ($caller eq 'reset_by_email') {
1325: $output .= qq|
1326: this.document.pserver.elements.uname.value =
1327: this.document.client.elements.uname.value;
1328: this.document.pserver.elements.udom.value =
1329: this.document.client.elements.udom.options[this.document.client.elements.udom.selectedIndex].value;
1330: |;
1331: }
1332: $ output .= qq|
1.52 raeburn 1333: this.document.pserver.submit();
1.3 matthew 1334: }
1335: </script>
1.94 raeburn 1336: |;
1337: }
1.3 matthew 1338:
1.94 raeburn 1339: sub client_form {
1340: my ($caller,$hexkey,$currentpass,$defdom) = @_;
1.99 www 1341: my %lt=&Apache::lonlocal::texthash(
1.115 raeburn 1342: 'email' => 'E-mail Address',
1.99 www 1343: 'username' => 'Username',
1344: 'domain' => 'Domain',
1345: 'currentpass' => 'Current Password',
1346: 'newpass' => 'New Password',
1347: 'confirmpass' => 'Confirm Password',
1.136 schafran 1348: 'changepass' => 'Save');
1.99 www 1349:
1.94 raeburn 1350: my $output = qq|
1.3 matthew 1351: <form name="client" >
1352: <table>
1.94 raeburn 1353: |;
1354: if ($caller eq 'reset_by_email') {
1355: $output .= qq|
1.99 www 1356: <tr><td class="LC_preferences_labeltext"><label for="email">$lt{'email'}</label>:</td>
1.97 raeburn 1357: <td><input type="text" name="email" size="30" /> </td></tr>
1.99 www 1358: <tr><td class="LC_preferences_labeltext"><label for="uname">$lt{'username'}</label>:</td>
1.94 raeburn 1359: <td>
1.97 raeburn 1360: <input type="text" name="uname" size="15" />
1.94 raeburn 1361: <input type="hidden" name="currentpass" value="$currentpass" />
1362: </td></tr>
1.115 raeburn 1363: <tr><td class="LC_preferences_labeltext"><label for="udom">$lt{'domain'}</label>:</td>
1.94 raeburn 1364: <td>
1365: |;
1366: $output .= &Apache::loncommon::select_dom_form($defdom,'udom').'
1367: </td>
1368: </tr>
1369: ';
1370: } else {
1371: $output .= qq|
1.99 www 1372: <tr><td class="LC_preferences_labeltext"><label for="currentpass">$lt{'currentpass'}</label></td>
1.4 matthew 1373: <td><input type="password" name="currentpass" size="10"/> </td></tr>
1.94 raeburn 1374: |;
1375: }
1376: $output .= <<"ENDFORM";
1.99 www 1377: <tr><td class="LC_preferences_labeltext"><label for="newpass_1">$lt{'newpass'}</label></td>
1.4 matthew 1378: <td><input type="password" name="newpass_1" size="10" /> </td></tr>
1.99 www 1379: <tr><td class="LC_preferences_labeltext"><label for="newpass_2">$lt{'confirmpass'}</label></td>
1.4 matthew 1380: <td><input type="password" name="newpass_2" size="10" /> </td></tr>
1.3 matthew 1381: <tr><td colspan="2" align="center">
1.149 bisitz 1382: <input type="button" value="$lt{'changepass'}" onClick="send();" />
1.3 matthew 1383: </table>
1.94 raeburn 1384: <input type="hidden" name="ukey_cpass" value="$hexkey->{'ukey_cpass'}" />
1385: <input type="hidden" name="lkey_cpass" value="$hexkey->{'lkey_cpass'}" />
1386: <input type="hidden" name="ukey_npass1" value="$hexkey->{'ukey_npass1'}" />
1387: <input type="hidden" name="lkey_npass1" value="$hexkey->{'lkey_npass1'}" />
1388: <input type="hidden" name="ukey_npass2" value="$hexkey->{'ukey_npass2'}" />
1389: <input type="hidden" name="lkey_npass2" value="$hexkey->{'lkey_npass2'}" />
1.3 matthew 1390: </form>
1391: </p>
1392: ENDFORM
1.94 raeburn 1393: return $output;
1394: }
1395:
1396: sub server_form {
1397: my ($logtoken,$caller,$mailtoken) = @_;
1398: my $action = '/adm/preferences';
1399: if ($caller eq 'reset_by_email') {
1400: $action = '/adm/resetpw';
1401: }
1402: my $output = qq|
1403: <form name="pserver" action="$action" method="post">
1404: <input type="hidden" name="logtoken" value="$logtoken" />
1405: <input type="hidden" name="currentpass" value="" />
1406: <input type="hidden" name="newpass_1" value="" />
1407: <input type="hidden" name="newpass_2" value="" />
1408: |;
1409: if ($caller eq 'reset_by_email') {
1410: $output .= qq|
1411: <input type="hidden" name="token" value="$mailtoken" />
1412: <input type="hidden" name="uname" value="" />
1413: <input type="hidden" name="udom" value="" />
1414:
1415: |;
1416: }
1417: $output .= qq|
1418: <input type="hidden" name="action" value="verify_and_change_pass" />
1419: </form>
1420: |;
1421: return $output;
1.3 matthew 1422: }
1423:
1424: sub verify_and_change_password {
1.94 raeburn 1425: my ($r,$caller,$mailtoken) = @_;
1426: my ($user,$domain,$homeserver);
1427: if ($caller eq 'reset_by_email') {
1428: $user = $env{'form.uname'};
1429: $domain = $env{'form.udom'};
1430: if ($user ne '' && $domain ne '') {
1431: $homeserver = &Apache::lonnet::homeserver($user,$domain);
1432: if ($homeserver eq 'no_host') {
1.99 www 1433: &passwordchanger($r,"<p>\n<span class='LC_error'>".
1434: &mt("Invalid username and/or domain")."</span>\n</p>",
1.94 raeburn 1435: $caller,$mailtoken);
1436: return 1;
1437: }
1438: } else {
1.99 www 1439: &passwordchanger($r,"<p>\n<span class='LC_error'>".
1440: &mt("Username and domain were blank")."</span>\n</p>",
1.94 raeburn 1441: $caller,$mailtoken);
1442: return 1;
1443: }
1444: } else {
1445: $user = $env{'user.name'};
1446: $domain = $env{'user.domain'};
1447: $homeserver = $env{'user.home'};
1448: }
1.3 matthew 1449: my $currentauth=&Apache::lonnet::queryauthenticate($user,$domain);
1.4 matthew 1450: # Check for authentication types that allow changing of the password.
1.94 raeburn 1451: if ($currentauth !~ /^(unix|internal):/) {
1452: if ($caller eq 'reset_by_email') {
1.99 www 1453: &passwordchanger($r,"<p>\n<span class='LC_error'>".
1454: &mt("Authentication type for this user can not be changed by this mechanism").
1455: "</span>\n</p>",
1.94 raeburn 1456: $caller,$mailtoken);
1457: return 1;
1458: } else {
1459: return;
1460: }
1461: }
1.3 matthew 1462: #
1.59 albertel 1463: my $currentpass = $env{'form.currentpass'};
1464: my $newpass1 = $env{'form.newpass_1'};
1465: my $newpass2 = $env{'form.newpass_2'};
1466: my $logtoken = $env{'form.logtoken'};
1.3 matthew 1467: # Check for empty data
1.4 matthew 1468: unless (defined($currentpass) &&
1469: defined($newpass1) &&
1470: defined($newpass2) ){
1.99 www 1471: &passwordchanger($r,"<p>\n<span class='LC_error'>".
1472: &mt("One or more password fields were blank").
1473: "</span>\n</p>",$caller,$mailtoken);
1.3 matthew 1474: return;
1475: }
1.16 albertel 1476: # Get the keys
1477: my $lonhost = $r->dir_config('lonHostID');
1.3 matthew 1478: my $tmpinfo = Apache::lonnet::reply('tmpget:'.$logtoken,$lonhost);
1479: if (($tmpinfo=~/^error/) || ($tmpinfo eq 'con_lost')) {
1.4 matthew 1480: # I do not a have a better idea about how to handle this
1.94 raeburn 1481: my $tryagain_text = &mt('Please log out and try again.');
1482: if ($caller eq 'reset_by_email') {
1483: $tryagain_text = &mt('Please try again later.');
1484: }
1.101 albertel 1485: my $unable=&mt("Unable to retrieve saved token for password decryption");
1.3 matthew 1486: $r->print(<<ENDERROR);
1487: <p>
1.99 www 1488: <span class="LC_error">$unable. $tryagain_text</span>
1.3 matthew 1489: </p>
1490: ENDERROR
1.4 matthew 1491: # Probably should log an error here
1.75 albertel 1492: return 1;
1.3 matthew 1493: }
1494: my ($ckey,$n1key,$n2key)=split(/&/,$tmpinfo);
1.4 matthew 1495: #
1.17 matthew 1496: $currentpass = &des_decrypt($ckey ,$currentpass);
1497: $newpass1 = &des_decrypt($n1key,$newpass1);
1498: $newpass2 = &des_decrypt($n2key,$newpass2);
1.94 raeburn 1499: #
1500: if ($caller eq 'reset_by_email') {
1501: my %data = &Apache::lonnet::tmpget($mailtoken);
1.117 raeburn 1502: if (keys(%data) == 0) {
1503: &passwordchanger($r,
1504: '<span class="LC_error">'.
1505: &mt('Could not verify current authentication.').' '.
1506: &mt('Please try again.').'</span>',$caller,$mailtoken);
1507: return 1;
1508: }
1.94 raeburn 1509: if ($currentpass ne $data{'temppasswd'}) {
1510: &passwordchanger($r,
1.99 www 1511: '<span class="LC_error">'.
1.110 bisitz 1512: &mt('Could not verify current authentication.').' '.
1513: &mt('Please try again.').'</span>',$caller,$mailtoken);
1.94 raeburn 1514: return 1;
1515: }
1516: }
1.3 matthew 1517: if ($newpass1 ne $newpass2) {
1.4 matthew 1518: &passwordchanger($r,
1.99 www 1519: '<span class="LC_error">'.
1.110 bisitz 1520: &mt('The new passwords you entered do not match.').' '.
1521: &mt('Please try again.').'</span>',$caller,$mailtoken);
1.75 albertel 1522: return 1;
1.4 matthew 1523: }
1524: if (length($newpass1) < 7) {
1525: &passwordchanger($r,
1.99 www 1526: '<span class="LC_error">'.
1.110 bisitz 1527: &mt('Passwords must be a minimum of 7 characters long.').' '.
1528: &mt('Please try again.').'</span>',$caller,$mailtoken);
1.75 albertel 1529: return 1;
1.3 matthew 1530: }
1.4 matthew 1531: #
1532: # Check for bad characters
1533: my $badpassword = 0;
1534: foreach (split(//,$newpass1)) {
1535: $badpassword = 1 if ((ord($_)<32)||(ord($_)>126));
1536: }
1537: if ($badpassword) {
1538: # I can't figure out how to enter bad characters on my browser.
1.99 www 1539: my $errormessage ='<span class="LC_error">'.
1.110 bisitz 1540: &mt('The password you entered contained illegal characters.').'<br />'.
1.99 www 1541: &mt('Valid characters are').(<<"ENDERROR");
1542: : space and <br />
1.4 matthew 1543: <pre>
1544: !"\#$%&\'()*+,-./0123456789:;<=>?\@
1545: ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_\`abcdefghijklmnopqrstuvwxyz{|}~
1.99 www 1546: </pre></span>
1.4 matthew 1547: ENDERROR
1.94 raeburn 1548: &passwordchanger($r,$errormessage,$caller,$mailtoken);
1549: return 1;
1.4 matthew 1550: }
1551: #
1552: # Change the password (finally)
1553: my $result = &Apache::lonnet::changepass
1.94 raeburn 1554: ($user,$domain,$currentpass,$newpass1,$homeserver,$caller);
1.4 matthew 1555: # Inform the user the password has (not?) been changed
1.126 droeschl 1556: my $message;
1.4 matthew 1557: if ($result =~ /^ok$/) {
1.144 raeburn 1558: $message = &mt('The password for [_1] was successfully changed.',$user);
1559: if ($caller eq 'reset_by_email') {
1560: $r->print($message.'<br />');
1561: } else {
1562: &print_main_menu($r, $message);
1563: }
1.126 droeschl 1564: # $r->print("<h3>".&mt('The password for [_1] was successfully changed',$user)."</h3>");
1.4 matthew 1565: } else {
1566: # error error: run in circles, scream and shout
1.145 schualex 1567: $message = &mt("The password for [_1] was not changed.",$user).' '.&mt('Please make sure your old password was entered correctly.');
1.144 raeburn 1568: unless ($caller eq 'reset_by_email') {
1569: &print_main_menu($r, $message);
1570: }
1.126 droeschl 1571: # $r->print("<h3><span class='LC_error'>".&mt("The password for [_1] was not changed",$user)."</span></h3>".
1572: # &mt('Please make sure your old password was entered correctly.'));
1.75 albertel 1573: return 1;
1.4 matthew 1574: }
1575: return;
1.3 matthew 1576: }
1577:
1.42 raeburn 1578: ################################################################
1579: # discussion display subroutines
1580: ################################################################
1581: sub discussionchanger {
1582: my $r = shift;
1.126 droeschl 1583: Apache::lonhtmlcommon::add_breadcrumb(
1584: { href => '/adm/preferences?action=changediscussions',
1585: text => 'Change Discussion Preferences'});
1.147 schafran 1586: $r->print(Apache::loncommon::start_page('Message Management'));
1.126 droeschl 1587: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Discussion Preferences'));
1.59 albertel 1588: my $user = $env{'user.name'};
1589: my $domain = $env{'user.domain'};
1.42 raeburn 1590: my %userenv = &Apache::lonnet::get
1.43 raeburn 1591: ('environment',['discdisplay','discmarkread']);
1592: my $discdisp = 'allposts';
1593: my $discmark = 'onmark';
1594:
1595: if (defined($userenv{'discdisplay'})) {
1596: unless ($userenv{'discdisplay'} eq '') {
1597: $discdisp = $userenv{'discdisplay'};
1598: }
1599: }
1600: if (defined($userenv{'discmarkread'})) {
1601: unless ($userenv{'discdisplay'} eq '') {
1602: $discmark = $userenv{'discmarkread'};
1603: }
1604: }
1605:
1606: my $newdisp = 'unread';
1607: my $newmark = 'ondisp';
1608:
1609: my $function = &Apache::loncommon::get_users_function();
1610: my $color = &Apache::loncommon::designparm($function.'.tabbg',
1.59 albertel 1611: $env{'user.domain'});
1.43 raeburn 1612: my %lt = &Apache::lonlocal::texthash(
1613: 'pref' => 'Display Preference',
1614: 'curr' => 'Current setting ',
1615: 'actn' => 'Action',
1.135 schafran 1616: 'sdpf' => 'Set display preferences for discussion posts for both discussion boards and individual resources in all your courses.',
1.43 raeburn 1617: 'prca' => 'Preferences can be set that determine',
1.135 schafran 1618: 'whpo' => 'Which posts are displayed when you display a discussion board or resource, and',
1.43 raeburn 1619: 'unwh' => 'Under what circumstances posts are identfied as "New"',
1620: 'allposts' => 'All posts',
1621: 'unread' => 'New posts only',
1622: 'ondisp' => 'Once displayed',
1623: 'onmark' => 'Once marked as read',
1624: 'disa' => 'Posts displayed?',
1625: 'npmr' => 'New posts cease to be identified as "New"?',
1626: 'thde' => 'The preferences you set here can be overridden within each individual discussion.',
1627: 'chgt' => 'Change to '
1628: );
1629: my $dispchange = $lt{'unread'};
1630: my $markchange = $lt{'ondisp'};
1631: my $currdisp = $lt{'allposts'};
1632: my $currmark = $lt{'onmark'};
1633:
1634: if ($discdisp eq 'unread') {
1635: $dispchange = $lt{'allposts'};
1636: $currdisp = $lt{'unread'};
1637: $newdisp = 'allposts';
1638: }
1639:
1640: if ($discmark eq 'ondisp') {
1641: $markchange = $lt{'onmark'};
1642: $currmark = $lt{'ondisp'};
1643: $newmark = 'onmark';
1.42 raeburn 1644: }
1.43 raeburn 1645:
1646: $r->print(<<"END");
1.88 albertel 1647: <form name="prefs" action="/adm/preferences" method="post">
1.42 raeburn 1648: <input type="hidden" name="action" value="verify_and_change_discussion" />
1649: <br />
1.87 albertel 1650: $lt{'sdpf'}<br /> $lt{'prca'} <ol><li>$lt{'whpo'}</li><li>$lt{'unwh'}</li></ol>
1.43 raeburn 1651: <br />
1652: <br />
1.82 albertel 1653: END
1654: $r->print(&Apache::loncommon::start_data_table());
1655: $r->print(<<"END");
1656: <tr>
1657: <th>$lt{'pref'}</th>
1658: <th>$lt{'curr'}</th>
1659: <th>$lt{'actn'}?</th>
1.43 raeburn 1660: </tr>
1.82 albertel 1661: END
1662: $r->print(&Apache::loncommon::start_data_table_row());
1663: $r->print(<<"END");
1.43 raeburn 1664: <td>$lt{'disa'}</td>
1665: <td>$lt{$discdisp}</td>
1.82 albertel 1666: <td><label><input type="checkbox" name="discdisp" /><input type="hidden" name="newdisp" value="$newdisp" /> $lt{'chgt'} "$dispchange"</label></td>
1667: END
1668: $r->print(&Apache::loncommon::end_data_table_row().
1669: &Apache::loncommon::start_data_table_row());
1670: $r->print(<<"END");
1.43 raeburn 1671: <td>$lt{'npmr'}</td>
1672: <td>$lt{$discmark}</td>
1.82 albertel 1673: <td><label><input type="checkbox" name="discmark" /><input type="hidden" name="newmark" value="$newmark" /> $lt{'chgt'} "$markchange"</label></td>
1.43 raeburn 1674: </tr>
1.82 albertel 1675: END
1676: $r->print(&Apache::loncommon::end_data_table_row().
1677: &Apache::loncommon::end_data_table());
1.142 zhu 1678:
1679: $r->print('<br /><br /><input type="submit" name="sub" value="'.&mt('Save').'" /><br /><br />'.&mt('Note').': '.$lt{'thde'}.'</form>');
1.42 raeburn 1680: }
1681:
1682: sub verify_and_change_discussion {
1683: my $r = shift;
1.59 albertel 1684: my $user = $env{'user.name'};
1685: my $domain = $env{'user.domain'};
1.42 raeburn 1686: my $message='';
1.59 albertel 1687: if (defined($env{'form.discdisp'}) ) {
1688: my $newdisp = $env{'form.newdisp'};
1.43 raeburn 1689: if ($newdisp eq 'unread') {
1.110 bisitz 1690: $message .=&mt('In discussions: only new posts will be displayed.').'<br />';
1.43 raeburn 1691: &Apache::lonnet::put('environment',{'discdisplay' => $newdisp});
1.116 raeburn 1692: &Apache::lonnet::appenv({'environment.discdisplay' => $newdisp});
1.43 raeburn 1693: } else {
1.110 bisitz 1694: $message .= &mt('In discussions: all posts will be displayed.').'<br />';
1.43 raeburn 1695: &Apache::lonnet::del('environment',['discdisplay']);
1.139 raeburn 1696: &Apache::lonnet::delenv('environment.discdisplay');
1.43 raeburn 1697: }
1698: }
1.59 albertel 1699: if (defined($env{'form.discmark'}) ) {
1700: my $newmark = $env{'form.newmark'};
1.43 raeburn 1701: if ($newmark eq 'ondisp') {
1.110 bisitz 1702: $message.=&mt('In discussions: new posts will be cease to be identified as "NEW" after display.').'<br />';
1.43 raeburn 1703: &Apache::lonnet::put('environment',{'discmarkread' => $newmark});
1.116 raeburn 1704: &Apache::lonnet::appenv({'environment.discmarkread' => $newmark});
1.43 raeburn 1705: } else {
1.110 bisitz 1706: $message.=&mt('In discussions: posts will be identified as "NEW" until marked as read by the reader.').'<br />';
1.43 raeburn 1707: &Apache::lonnet::del('environment',['discmarkread']);
1.139 raeburn 1708: &Apache::lonnet::delenv('environment.discmarkread');
1.43 raeburn 1709: }
1.42 raeburn 1710: }
1.126 droeschl 1711: # $r->print(<<ENDVCSCREEN);
1712: #$message
1713: #ENDVCSCREEN
1714: print_main_menu($r, $message);
1.42 raeburn 1715: }
1716:
1.63 raeburn 1717: ################################################################
1718: # Subroutines for page display on course access (Course Coordinators)
1719: ################################################################
1720: sub coursedisplaychanger {
1721: my $r = shift;
1.126 droeschl 1722: Apache::lonhtmlcommon::add_breadcrumb(
1723: { href => '/adm/preferences?action=changecourseinit',
1724: text => 'Change Course Init. Pref.'});
1725: $r->print(Apache::loncommon::start_page('Change Course Initialization Preference'));
1726: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Course Init. Pref.'));
1.63 raeburn 1727: my $user = $env{'user.name'};
1728: my $domain = $env{'user.domain'};
1.66 albertel 1729: my %userenv = &Apache::lonnet::get('environment',['course_init_display']);
1.71 raeburn 1730: my $currvalue = 'whatsnew';
1.73 albertel 1731: my $firstselect = '';
1732: my $whatsnewselect = 'checked="checked"';
1.71 raeburn 1733: if (exists($userenv{'course_init_display'})) {
1734: if ($userenv{'course_init_display'} eq 'firstres') {
1735: $currvalue = 'firstres';
1.73 albertel 1736: $firstselect = 'checked="checked"';
1737: $whatsnewselect = '';
1.71 raeburn 1738: }
1.63 raeburn 1739: }
1.134 bisitz 1740: my %pagenames = &Apache::lonlocal::texthash(
1.71 raeburn 1741: firstres => 'First resource',
1.143 hauer 1742: whatsnew => "What's New Page",
1.71 raeburn 1743: );
1.134 bisitz 1744: my $whatsnew_off=&mt('Display the [_1]first resource[_2] in the course.','<b>','</b>');
1.143 hauer 1745: my $whatsnew_on=&mt("Display the [_1]What's New Page[_2] - a summary of items in the course which require attention.",'<b>','</b>');
1.63 raeburn 1746:
1.134 bisitz 1747: $r->print('<br /><b>'
1748: .&mt('Set the default page to be displayed when you select a course role')
1749: .'</b> '
1750: .&mt('(Currently: [_1])',$pagenames{$currvalue})
1751: .'<br />'
1.143 hauer 1752: .&mt("The global user preference you set for your courses can be overridden in an individual course by setting a course specific setting via the [_1]What's New Page[_2] in the course.",'<i>','</i>')
1.134 bisitz 1753: .'<br /><br />'
1754: );
1.63 raeburn 1755: $r->print(<<ENDLSCREEN);
1.88 albertel 1756: <form name="prefs" action="/adm/preferences" method="post">
1.63 raeburn 1757: <input type="hidden" name="action" value="verify_and_change_coursepage" />
1.72 albertel 1758: <br />
1.65 albertel 1759: <label><input type="radio" name="newdisp" value="firstres" $firstselect /> $whatsnew_off</label><br />
1.70 raeburn 1760: <label><input type="radio" name="newdisp" value="whatsnew" $whatsnewselect /> $whatsnew_on</label><input type="hidden" name="refpage" value="$env{'form.refpage'}" />
1.63 raeburn 1761: ENDLSCREEN
1.140 schafran 1762: $r->print('<br /><br /><input type="submit" value="'.&mt('Save').'" />
1.63 raeburn 1763: </form>');
1764: }
1765:
1766: sub verify_and_change_coursepage {
1767: my $r = shift;
1768: my $message='';
1769: my %lt = &Apache::lonlocal::texthash(
1.70 raeburn 1770: 'defs' => 'Default now set',
1.71 raeburn 1771: 'when' => 'when you select a course role from the roles screen',
1.63 raeburn 1772: 'ywbt' => 'you will be taken to the start of the course.',
1773: 'apwb' => 'a page will be displayed that lists items in the course that may require action from you.',
1774: 'gtts' => 'Go to the start of the course',
1.146 hauer 1775: 'dasp' => "Display the What's New Page",
1.63 raeburn 1776: );
1777: my $newdisp = $env{'form.newdisp'};
1.70 raeburn 1778: $message = '<b>'.$lt{'defs'}.'</b>: '.$lt{'when'}.', ';
1.63 raeburn 1779: if ($newdisp eq 'firstres') {
1.87 albertel 1780: $message .= $lt{'ywbt'}.'<br />';
1.63 raeburn 1781: &Apache::lonnet::put('environment',{'course_init_display' => $newdisp});
1.116 raeburn 1782: &Apache::lonnet::appenv({'environment.course_init_display' => $newdisp});
1.63 raeburn 1783: } else {
1.87 albertel 1784: $message .= $lt{'apwb'}.'<br />';
1.63 raeburn 1785: &Apache::lonnet::del('environment',['course_init_display']);
1.139 raeburn 1786: &Apache::lonnet::delenv('environment.course_init_display');
1.63 raeburn 1787: }
1.70 raeburn 1788: my $refpage = $env{'form.refpage'};
1.63 raeburn 1789: if (($env{'request.course.fn'}) && ($env{'request.course.id'})) {
1790: if ($newdisp eq 'firstres') {
1791: my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
1792: my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
1793: my ($furl,$ferr)=
1794: &Apache::lonuserstate::readmap($cdom.'/'.$cnum);
1795: $message .= '<br /><font size="+1"><a href="'.$furl.'">'.$lt{'gtts'}.' <i>'.&mt('now').'</i></a></font>';
1796: } else {
1.70 raeburn 1797: $message .= '<br /><font size="+1"><a href="/adm/whatsnew?refpage='.
1798: $refpage.'">'.$lt{'dasp'}.'</a></font>';
1.63 raeburn 1799: }
1800: }
1.126 droeschl 1801: # $r->print(<<ENDVCSCREEN);
1802: #$message
1803: #<br /><br />
1804: #ENDVCSCREEN
1805: print_main_menu($r, $message);
1.63 raeburn 1806: }
1807:
1.126 droeschl 1808: sub print_main_menu {
1809: my ($r, $message) = @_;
1810: # Determine current authentication method
1811: my $user = $env{'user.name'};
1812: my $domain = $env{'user.domain'};
1813: my $currentauth=&Apache::lonnet::queryauthenticate($user,$domain);
1814:
1815: # build the data structure for menu generation
1816: my $aboutmeurl='/adm/'.$env{'user.domain'}.'/'.$env{'user.name'}.'/aboutme';
1817: my $role = ($env{'user.adv'} ? 'Roles' : 'Course');
1.131 raeburn 1818: my %permissions;
1819: if (&Apache::lonnet::usertools_access($user,$domain,'aboutme')) {
1820: $permissions{'aboutme'} = 'F';
1821: }
1.126 droeschl 1822: my @menu=
1823: ({ categorytitle=>'Personal Data',
1824: items =>[
1.141 weissno 1825: { linktext => 'Personal Information Page',
1.126 droeschl 1826: url => $aboutmeurl,
1.131 raeburn 1827: permission => $permissions{'aboutme'},
1.126 droeschl 1828: #help => 'Prefs_About_Me',
1829: icon => 'system-users.png',
1830: linktitle => 'Edit information about yourself that should be displayed on your public profile.'
1831: },
1832: { linktext => 'Screen Name',
1833: url => '/adm/preferences?action=changescreenname',
1834: permission => 'F',
1835: #help => 'Prefs_Screen_Name_Nickname',
1836: icon => 'preferences-desktop-font.png',
1837: linktitle => 'Change the name that is displayed in your posts.'
1838: },
1839: ]
1840: },
1841: { categorytitle=>'Page Display Settings',
1842: items =>[
1843: { linktext => 'Color Scheme',
1844: url => '/adm/preferences?action=changecolors',
1845: permission => 'F',
1846: #help => 'Change_Colors',
1847: icon => 'preferences-desktop-theme.png',
1848: linktitle => 'Change LON-CAPA default colors.'
1849: },
1850: { linktext => 'Menu Display',
1851: url => '/adm/preferences?action=changeicons',
1852: permission => 'F',
1853: #help => '',
1854: icon => 'preferences-system-windows.png',
1855: linktitle => 'Change whether the menus are displayed with buttons, icons or icons and text.'
1856: }
1857:
1858: ]
1859: },
1860: { categorytitle=>'Content Display Settings',
1861: items =>[
1862: { linktext => 'Language',
1863: url => '/adm/preferences?action=changelanguages',
1864: permission => 'F',
1865: #help => 'Prefs_Language',
1866: icon => 'preferences-desktop-locale.png',
1.127 droeschl 1867: linktitle => 'Choose the default language for this user.'
1.126 droeschl 1868: },
1.128 droeschl 1869: { linktext => 'WYSIWYG Editor',
1.126 droeschl 1870: url => '/adm/preferences?action=changewysiwyg',
1871: permission => 'F',
1872: #help => '',
1873: icon => 'edit-select-all.png',
1874: linktitle => 'Enable or disable the WYSIWYG-Editor.'
1875: },
1.128 droeschl 1876: { linktext => $role.' Page',
1.126 droeschl 1877: url => '/adm/preferences?action=changerolespref',
1878: permission => 'F',
1879: #help => '',
1880: icon => 'sctr.png',
1881: linktitle => 'Configure the roles hotlist.'
1882: },
1.127 droeschl 1883: { linktext => 'Display of Scientific Equations',
1.126 droeschl 1884: url => '/adm/preferences?action=changetexenginepref',
1885: permission => 'F',
1886: #help => '',
1887: icon => 'stat.png',
1.127 droeschl 1888: linktitle => 'Change how Scientific Equations are displayed.'
1.126 droeschl 1889: },
1890: ]
1891: },
1.128 droeschl 1892: { categorytitle=>'Message Management',
1893: items =>[
1894: { linktext => 'Messages & Notifications',
1895: url => '/adm/preferences?action=changemsgforward',
1896: permission => 'F',
1897: #help => 'Prefs_Messages',
1898: icon => 'mail-reply-all.png',
1899: linktitle => 'Change messageforwarding or notifications settings.'
1900: },
1901: { linktext => 'Discussion Display',
1902: url => '/adm/preferences?action=changediscussions',
1903: permission => 'F',
1904: #help => 'Change_Discussion_Display',
1905: icon => 'mail-message-new.png',
1.135 schafran 1906: linktitle => 'Set display preferences for discussion posts for both discussion boards and individual resources in all your courses.'
1.128 droeschl 1907: },
1908: ]
1909: },
1.126 droeschl 1910: { categorytitle=>'Other',
1911: items =>[
1912: { linktext => 'Register Response Devices ("Clickers")',
1913: url => '/adm/preferences?action=changeclicker',
1914: permission => 'F',
1915: #help => '',
1916: icon => 'network-workgroup.png',
1917: linktitle => 'Register your clicker.'
1918: },
1919: ]
1920: },
1921: );
1922:
1923: if ($currentauth =~ /^(unix|internal):/) {
1924: push(@{ $menu[0]->{items} }, {
1925: linktext => 'Password',
1926: url => '/adm/preferences?action=changepass',
1927: permission => 'F',
1928: #help => 'Change_Password',
1929: icon => 'emblem-readonly.png',
1930: linktitle => 'Change your password.',
1931: });
1932: }
1933: if ($env{'environment.remote'} eq 'off') {
1934: push(@{ $menu[1]->{items} }, {
1935: linktext => 'Launch Remote Control',
1936: url => '/adm/remote?url=/adm/preferences?action=launch',
1937: permission => 'F',
1938: #help => '',
1939: icon => 'network-wireless.png',
1940: linktitle => 'Launch the remote control for LON-CAPA.',
1941: });
1942: }else{
1943: push(@{ $menu[1]->{items} }, {
1944: linktext => 'Collapse Remote Control',
1945: url => '/adm/remote?url=/adm/preferences?action=collapse',
1946: permission => 'F',
1947: #help => '',
1948: icon => 'network-wireless.png',
1949: linktitle => 'Collapse the remote control for LON-CAPA.',
1950: });
1951: }
1952: my %author_roles = &Apache::lonnet::get_my_roles($user,$domain,'userroles','',['au']);
1953: if (keys(%author_roles) > 0) {
1954: push(@{ $menu[4]->{items} }, {
1955: linktext => 'Restrict Domain Coordinator Access',
1956: url => '/adm/preferences?action=changedomcoord',
1957: permission => 'F',
1958: #help => '',
1959: icon => 'system-lock-screen.png',
1960: linktitle => 'Restrict domain coordinator access.',
1961: });
1962: }
1963:
1964: if (&Apache::lonnet::allowed('whn',$env{'request.course.id'})
1965: || &Apache::lonnet::allowed('whn',$env{'request.course.id'}.'/'
1966: .$env{'request.course.sec'})) {
1967: push(@{ $menu[4]->{items} }, {
1.128 droeschl 1968: linktext => 'Course Initialization',
1.126 droeschl 1969: url => '/adm/preferences?action=changecourseinit',
1970: permission => 'F',
1971: #help => '',
1972: icon => 'edit-copy.png',
1973: linktitle => 'Set the default page to be displayed when you select a course role.',
1974: });
1975:
1976: }
1977: if ($env{'user.name'} =~ /^(albertel|fox|foxr|kortemey|korte|raeburn)$/) {
1978: push(@{ $menu[4]->{items} }, {
1979: linktext => 'Toggle Debug Messages (Current:'.$env{'user.debug'}.')',
1980: url => '/adm/preferences?action=debugtoggle',
1981: permission => 'F',
1982: #help => '',
1983: icon => 'blog.png',
1984: linktitle => 'Toggle Debug Messages.',
1985: });
1986: }
1987:
1.147 schafran 1988: $r->print(&Apache::loncommon::start_page('My Space'));
1.126 droeschl 1989: $r->print(Apache::lonhtmlcommon::breadcrumbs('Change Preferences'));
1990: $r->print($message);
1991: $r->print(Apache::lonhtmlcommon::generate_menu(@menu));
1992: $r->print(Apache::loncommon::end_page());
1993: }
1.63 raeburn 1994:
1.4 matthew 1995: ######################################################
1996: # other handler subroutines #
1997: ######################################################
1998:
1.3 matthew 1999: ################################################################
2000: # Main handler #
2001: ################################################################
1.126 droeschl 2002: sub handler {
2003: my $r = shift;
2004: Apache::loncommon::content_type($r,'text/html');
2005: # Some pages contain DES keys and should not be cached.
2006: Apache::loncommon::no_cache($r);
2007: $r->send_http_header;
2008: return OK if $r->header_only;
2009: #
2010: Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},
2011: ['action','wysiwyg','returnurl','refpage']);
2012: #
2013: Apache::lonhtmlcommon::clear_breadcrumbs();
2014: Apache::lonhtmlcommon::add_breadcrumb
2015: ({href => '/adm/preferences',
1.150 droeschl 2016: text => 'Set User Preferences',
2017: help =>
2018: 'Prefs_About_Me,Prefs_Language,Prefs_Screen_Name_Nickname,Change_Colors,Change_Password,Prefs_Messages,Change_Discussion_Display'});
1.126 droeschl 2019: if(!exists $env{'form.action'}) {
1.150 droeschl 2020: &print_main_menu($r);
1.126 droeschl 2021: }elsif($env{'form.action'} eq 'changepass'){
2022: &passwordchanger($r);
2023: }elsif($env{'form.action'} eq 'verify_and_change_pass'){
2024: &verify_and_change_password($r);
2025: }elsif($env{'form.action'} eq 'changescreenname'){
2026: &screennamechanger($r);
2027: }elsif($env{'form.action'} eq 'verify_and_change_screenname'){
2028: &verify_and_change_screenname($r);
2029: }elsif($env{'form.action'} eq 'changemsgforward'){
2030: &msgforwardchanger($r);
2031: }elsif($env{'form.action'} eq 'verify_and_change_msgforward'){
2032: &verify_and_change_msgforward($r);
2033: }elsif($env{'form.action'} eq 'changecolors'){
2034: &colorschanger($r);
2035: }elsif($env{'form.action'} eq 'verify_and_change_colors'){
2036: &verify_and_change_colors($r);
2037: }elsif($env{'form.action'} eq 'changelanguages'){
2038: &languagechanger($r);
2039: }elsif($env{'form.action'} eq 'verify_and_change_languages'){
2040: &verify_and_change_languages($r);
2041: }elsif($env{'form.action'} eq 'changewysiwyg'){
2042: &wysiwygchanger($r);
2043: }elsif($env{'form.action'} eq 'set_wysiwyg'){
2044: &verify_and_change_wysiwyg($r);
2045: }elsif($env{'form.action'} eq 'changediscussions'){
2046: &discussionchanger($r);
2047: }elsif($env{'form.action'} eq 'verify_and_change_discussion'){
2048: &verify_and_change_discussion($r);
2049: }elsif($env{'form.action'} eq 'changerolespref'){
2050: &rolesprefchanger($r);
2051: }elsif($env{'form.action'} eq 'verify_and_change_rolespref'){
2052: &verify_and_change_rolespref($r);
2053: }elsif($env{'form.action'} eq 'changetexenginepref'){
2054: &texenginechanger($r);
2055: }elsif($env{'form.action'} eq 'verify_and_change_texengine'){
2056: &verify_and_change_texengine($r);
2057: }elsif($env{'form.action'} eq 'changeicons'){
2058: &iconchanger($r);
2059: }elsif($env{'form.action'} eq 'verify_and_change_icons'){
2060: &verify_and_change_icons($r);
2061: }elsif($env{'form.action'} eq 'changeclicker'){
2062: &clickerchanger($r);
2063: }elsif($env{'form.action'} eq 'verify_and_change_clicker'){
2064: &verify_and_change_clicker($r);
2065: }elsif($env{'form.action'} eq 'changedomcoord'){
2066: &domcoordchanger($r);
2067: }elsif($env{'form.action'} eq 'verify_and_change_domcoord'){
2068: &verify_and_change_domcoord($r);
2069: }elsif($env{'form.action'} eq 'lockwarning'){
2070: &lockwarning($r);
2071: }elsif($env{'form.action'} eq 'verify_and_change_locks'){
2072: &verify_and_change_lockwarning($r);
2073: }elsif($env{'form.action'} eq 'changecourseinit'){
2074: &coursedisplaychanger($r);
2075: }elsif($env{'form.action'} eq 'verify_and_change_coursepage'){
2076: &verify_and_change_coursepage($r);
2077: }elsif($env{'form.action'} eq 'debugtoggle'){
2078: toggle_debug();
1.150 droeschl 2079: print_main_menu($r);
1.126 droeschl 2080: }
2081:
2082: return OK;
2083:
2084:
2085: }
2086: #remove when done
2087: #old handler routine
2088: sub handler2 {
1.1 www 2089: my $r = shift;
1.59 albertel 2090: my $user = $env{'user.name'};
2091: my $domain = $env{'user.domain'};
1.31 www 2092: &Apache::loncommon::content_type($r,'text/html');
1.4 matthew 2093: # Some pages contain DES keys and should not be cached.
2094: &Apache::loncommon::no_cache($r);
1.1 www 2095: $r->send_http_header;
2096: return OK if $r->header_only;
1.9 matthew 2097: #
1.35 matthew 2098: &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},
1.70 raeburn 2099: ['action','wysiwyg','returnurl','refpage']);
1.35 matthew 2100: #
2101: &Apache::lonhtmlcommon::clear_breadcrumbs();
2102: &Apache::lonhtmlcommon::add_breadcrumb
2103: ({href => '/adm/preferences',
2104: text => 'Set User Preferences'});
2105:
2106: my @Options;
2107: # Determine current authentication method
2108: my $currentauth=&Apache::lonnet::queryauthenticate($user,$domain);
2109: if ($currentauth =~ /^(unix|internal):/) {
2110: push (@Options,({ action => 'changepass',
1.40 www 2111: linktext => 'Change Password',
1.35 matthew 2112: href => '/adm/preferences',
2113: help => 'Change_Password',
2114: subroutine => \&passwordchanger,
2115: breadcrumb =>
2116: { href => '/adm/preferences?action=changepass',
2117: text => 'Change Password'},
2118: },
2119: { action => 'verify_and_change_pass',
2120: subroutine => \&verify_and_change_password,
2121: breadcrumb =>
2122: { href =>'/adm/preferences?action=changepass',
2123: text => 'Change Password'},
1.75 albertel 2124: printmenu => 'not_on_error',
1.35 matthew 2125: }));
2126: }
2127: push (@Options,({ action => 'changescreenname',
2128: linktext => 'Change Screen Name',
2129: href => '/adm/preferences',
2130: help => 'Prefs_Screen_Name_Nickname',
2131: subroutine => \&screennamechanger,
2132: breadcrumb =>
2133: { href => '/adm/preferences?action=changescreenname',
2134: text => 'Change Screen Name'},
2135: },
2136: { action => 'verify_and_change_screenname',
2137: subroutine => \&verify_and_change_screenname,
2138: breadcrumb =>
2139: { href => '/adm/preferences?action=changescreenname',
2140: text => 'Change Screen Name'},
2141: printmenu => 'yes',
2142: }));
2143:
2144: push (@Options,({ action => 'changemsgforward',
1.129 schafran 2145: linktext => 'Change Message Forwarding and Notification E-mail Addresses',
1.35 matthew 2146: href => '/adm/preferences',
1.113 raeburn 2147: help => 'Prefs_Messages',
1.35 matthew 2148: breadcrumb =>
2149: { href => '/adm/preferences?action=changemsgforward',
1.113 raeburn 2150: text => 'Change Message Forwarding/Notification'},
1.35 matthew 2151: subroutine => \&msgforwardchanger,
2152: },
2153: { action => 'verify_and_change_msgforward',
1.113 raeburn 2154: help => 'Prefs_Messages',
1.35 matthew 2155: breadcrumb =>
2156: { href => '/adm/preferences?action=changemsgforward',
1.113 raeburn 2157: text => 'Change Message Forwarding/Notification'},
1.126 droeschl 2158: printmenu => 'yes',
1.35 matthew 2159: subroutine => \&verify_and_change_msgforward }));
2160: my $aboutmeaction=
1.59 albertel 2161: '/adm/'.$env{'user.domain'}.'/'.$env{'user.name'}.'/aboutme';
1.35 matthew 2162: push (@Options,{ action => 'none',
2163: linktext =>
1.141 weissno 2164: q{Edit the Personal Information Page},
1.45 www 2165: help => 'Prefs_About_Me',
1.35 matthew 2166: href => $aboutmeaction});
2167: push (@Options,({ action => 'changecolors',
2168: linktext => 'Change Color Scheme',
2169: href => '/adm/preferences',
2170: help => 'Change_Colors',
2171: breadcrumb =>
2172: { href => '/adm/preferences?action=changecolors',
2173: text => 'Change Colors'},
2174: subroutine => \&colorschanger,
2175: },
2176: { action => 'verify_and_change_colors',
2177: breadcrumb =>
2178: { href => '/adm/preferences?action=changecolors',
2179: text => 'Change Colors'},
2180: printmenu => 'yes',
2181: subroutine => \&verify_and_change_colors,
2182: }));
2183: push (@Options,({ action => 'changelanguages',
1.39 www 2184: linktext => 'Change Language Preferences',
1.35 matthew 2185: href => '/adm/preferences',
1.45 www 2186: help => 'Prefs_Language',
1.35 matthew 2187: breadcrumb=>
2188: { href => '/adm/preferences?action=changelanguages',
2189: text => 'Change Language'},
2190: subroutine => \&languagechanger,
2191: },
2192: { action => 'verify_and_change_languages',
2193: breadcrumb=>
2194: {href => '/adm/preferences?action=changelanguages',
2195: text => 'Change Language'},
2196: printmenu => 'yes',
2197: subroutine=>\&verify_and_change_languages, }
2198: ));
1.44 www 2199: push (@Options,({ action => 'changewysiwyg',
2200: linktext => 'Change WYSIWYG Editor Preferences',
2201: href => '/adm/preferences',
2202: breadcrumb =>
2203: { href => '/adm/preferences?action=changewysiwyg',
2204: text => 'Change WYSIWYG Preferences'},
2205: subroutine => \&wysiwygchanger,
2206: },
2207: { action => 'set_wysiwyg',
2208: breadcrumb =>
2209: { href => '/adm/preferences?action=changewysiwyg',
2210: text => 'Change WYSIWYG Preferences'},
2211: printmenu => 'yes',
2212: subroutine => \&verify_and_change_wysiwyg, }
2213: ));
1.42 raeburn 2214: push (@Options,({ action => 'changediscussions',
2215: linktext => 'Change Discussion Display Preferences',
2216: href => '/adm/preferences',
1.46 raeburn 2217: help => 'Change_Discussion_Display',
1.42 raeburn 2218: breadcrumb =>
2219: { href => '/adm/preferences?action=changediscussions',
1.43 raeburn 2220: text => 'Change Discussion Preferences'},
1.42 raeburn 2221: subroutine => \&discussionchanger,
2222: },
2223: { action => 'verify_and_change_discussion',
2224: breadcrumb =>
2225: { href => '/adm/preferences?action=changediscussions',
1.43 raeburn 2226: text => 'Change Discussion Preferences'},
1.42 raeburn 2227: printmenu => 'yes',
2228: subroutine => \&verify_and_change_discussion, }
2229: ));
1.96 albertel 2230:
2231: my $role = ($env{'user.adv'} ? 'Roles' : 'Course');
1.50 albertel 2232: push (@Options,({ action => 'changerolespref',
1.96 albertel 2233: linktext => 'Change '.$role.' Page Preferences',
1.50 albertel 2234: href => '/adm/preferences',
2235: subroutine => \&rolesprefchanger,
2236: breadcrumb =>
2237: { href => '/adm/preferences?action=changerolespref',
1.96 albertel 2238: text => 'Change '.$role.' Page Pref'},
1.50 albertel 2239: },
2240: { action => 'verify_and_change_rolespref',
2241: subroutine => \&verify_and_change_rolespref,
2242: breadcrumb =>
2243: { href => '/adm/preferences?action=changerolespref',
1.96 albertel 2244: text => 'Change '.$role.' Page Preferences'},
1.50 albertel 2245: printmenu => 'yes',
2246: }));
2247:
1.54 albertel 2248: push (@Options,({ action => 'changetexenginepref',
2249: linktext => 'Change How Math Equations Are Displayed',
2250: href => '/adm/preferences',
2251: subroutine => \&texenginechanger,
2252: breadcrumb =>
2253: { href => '/adm/preferences?action=changetexenginepref',
2254: text => 'Change Math Pref'},
2255: },
2256: { action => 'verify_and_change_texengine',
2257: subroutine => \&verify_and_change_texengine,
2258: breadcrumb =>
2259: { href => '/adm/preferences?action=changetexenginepref',
2260: text => 'Change Math Preferences'},
2261: printmenu => 'yes',
2262: }));
1.85 albertel 2263:
2264: if ($env{'environment.remote'} eq 'off') {
2265: push (@Options,({ action => 'launch',
2266: linktext => 'Launch Remote Control',
2267: href => '/adm/remote?url=/adm/preferences',
2268: }));
2269: } else {
2270: push (@Options,({ action => 'collapse',
2271: linktext => 'Collapse Remote Control',
2272: href => '/adm/remote?url=/adm/preferences',
2273: }));
2274: }
2275:
1.98 www 2276: push (@Options,({ action => 'changeicons',
1.100 www 2277: linktext => 'Change How Menus are Displayed',
1.98 www 2278: href => '/adm/preferences',
2279: subroutine => \&iconchanger,
2280: breadcrumb =>
2281: { href => '/adm/preferences?action=changeicons',
2282: text => 'Change Main Menu'},
2283: },
2284: { action => 'verify_and_change_icons',
2285: subroutine => \&verify_and_change_icons,
2286: breadcrumb =>
2287: { href => '/adm/preferences?action=changeicons',
2288: text => 'Change Main Menu'},
2289: printmenu => 'yes',
2290: }));
2291:
1.106 www 2292: push (@Options,({ action => 'changeclicker',
2293: linktext => 'Register Response Devices ("Clickers")',
2294: href => '/adm/preferences',
2295: subroutine => \&clickerchanger,
2296: breadcrumb =>
1.118 www 2297: { href => '/adm/preferences?action=changeclicker',
1.106 www 2298: text => 'Register Clicker'},
2299: },
2300: { action => 'verify_and_change_clicker',
2301: subroutine => \&verify_and_change_clicker,
2302: breadcrumb =>
2303: { href => '/adm/preferences?action=changeclicker',
2304: text => 'Register Clicker'},
2305: printmenu => 'yes',
2306: }));
1.125 raeburn 2307: my %author_roles = &Apache::lonnet::get_my_roles($user,$domain,'userroles','',['au']);
2308: if (keys(%author_roles) > 0) {
1.119 www 2309: push (@Options,({ action => 'changedomcoord',
2310: linktext => 'Restrict Domain Coordinator Access',
2311: href => '/adm/preferences',
2312: subroutine => \&domcoordchanger,
2313: breadcrumb =>
2314: { href => '/adm/preferences?action=changedomcoord',
2315: text => 'Restrict Domain Coordinator Access'},
2316: },
2317: { action => 'verify_and_change_domcoord',
2318: subroutine => \&verify_and_change_domcoord,
2319: breadcrumb =>
2320: { href => '/adm/preferences?action=changedomcoord',
2321: text => 'Restrict Domain Coordinator Access'},
2322: printmenu => 'yes',
2323: }));
2324: }
1.105 www 2325:
1.118 www 2326: push (@Options,({ action => 'lockwarning',
2327: subroutine => \&lockwarning,
2328: breadcrumb =>
2329: { href => '/adm/preferences?action=lockwarning',
2330: text => 'Lock Warnings'},
2331: },
2332: { action => 'verify_and_change_locks',
2333: subroutine => \&verify_and_change_lockwarning,
2334: breadcrumb =>
2335: { href => '/adm/preferences?action=lockwarning',
2336: text => 'Lockwarnings'},
2337: printmenu => 'yes',
2338: }));
2339:
1.105 www 2340:
1.74 albertel 2341: if (&Apache::lonnet::allowed('whn',$env{'request.course.id'})
2342: || &Apache::lonnet::allowed('whn',$env{'request.course.id'}.'/'
2343: .$env{'request.course.sec'})) {
1.63 raeburn 2344: push (@Options,({ action => 'changecourseinit',
2345: linktext => 'Change Course Initialization Preference',
2346: href => '/adm/preferences',
2347: subroutine => \&coursedisplaychanger,
2348: breadcrumb =>
2349: { href => '/adm/preferences?action=changecourseinit',
2350: text => 'Change Course Init. Pref.'},
2351: },
2352: { action => 'verify_and_change_coursepage',
2353: breadcrumb =>
2354: { href => '/adm/preferences?action=changecourseinit', text => 'Change Course Initialization Preference'},
2355: printmenu => 'yes',
2356: subroutine => \&verify_and_change_coursepage,
2357: }));
2358: }
1.50 albertel 2359:
1.119 www 2360: if ($env{'user.name'} =~ /^(albertel|fox|foxr|kortemey|korte|raeburn)$/) {
1.35 matthew 2361: push (@Options,({ action => 'debugtoggle',
2362: printmenu => 'yes',
2363: subroutine => \&toggle_debug,
2364: }));
2365: }
1.76 albertel 2366:
2367: $r->print(&Apache::loncommon::start_page('Change Preferences'));
2368:
1.35 matthew 2369: my $call = undef;
1.48 albertel 2370: my $help = undef;
1.35 matthew 2371: my $printmenu = 'yes';
2372: foreach my $option (@Options) {
1.59 albertel 2373: if ($option->{'action'} eq $env{'form.action'}) {
1.35 matthew 2374: $call = $option->{'subroutine'};
2375: $printmenu = $option->{'printmenu'};
2376: if (exists($option->{'breadcrumb'})) {
2377: &Apache::lonhtmlcommon::add_breadcrumb
2378: ($option->{'breadcrumb'});
2379: }
1.48 albertel 2380: $help=$option->{'help'};
1.35 matthew 2381: }
2382: }
1.81 albertel 2383: $r->print(&Apache::lonhtmlcommon::breadcrumbs('Change Preferences',$help));
1.75 albertel 2384: my $error;
1.35 matthew 2385: if (defined($call)) {
1.75 albertel 2386: $error = $call->($r);
1.35 matthew 2387: }
1.75 albertel 2388: if ( ( ($printmenu eq 'yes')
2389: || ($printmenu eq 'not_on_error' && !$error) )
2390: && (!$env{'form.returnurl'})) {
1.35 matthew 2391: my $optionlist = '<table cellpadding="5">';
1.59 albertel 2392: if ($env{'user.name'} =~
1.62 raeburn 2393: /^(albertel|kortemey|fox|foxr|korte|hallmat3|turtle|raeburn)$/
1.35 matthew 2394: ) {
2395: push (@Options,({ action => 'debugtoggle',
2396: linktext => 'Toggle Debug Messages',
2397: text => 'Current Debug status is -'.
1.59 albertel 2398: $env{'user.debug'}.'-.',
1.35 matthew 2399: href => '/adm/preferences',
2400: printmenu => 'yes',
2401: subroutine => \&toggle_debug,
2402: }));
2403: }
2404: foreach my $option(@Options) {
2405: my $optiontext = '';
2406: if (exists($option->{'href'})) {
1.85 albertel 2407: $option->{'href_args'}{'action'}=$option->{'action'};
2408: $optiontext .=
2409: '<a href="'.&add_get_param($option->{'href'},
2410: $option->{'href_args'}).'">'.
1.47 albertel 2411: &mt($option->{'linktext'}).'</a>';
1.35 matthew 2412: }
2413: if (exists($option->{'text'})) {
1.47 albertel 2414: $optiontext .= ' '.&mt($option->{'text'});
1.35 matthew 2415: }
2416: if ($optiontext ne '') {
2417: $optiontext = '<font size="+1">'.$optiontext.'</font>';
2418: my $helplink = ' ';
2419: if (exists($option->{'help'})) {
2420: $helplink = &Apache::loncommon::help_open_topic
2421: ($option->{'help'});
2422: }
2423: $optionlist .= '<tr>'.
2424: '<td>'.$helplink.'</td>'.
2425: '<td>'.$optiontext.'</td>'.
2426: '</tr>';
2427: }
1.13 www 2428: }
1.35 matthew 2429: $optionlist .= '</table>';
2430: $r->print($optionlist);
1.59 albertel 2431: } elsif ($env{'form.returnurl'}) {
2432: $r->print('<br /><a href="'.$env{'form.returnurl'}.'"><font size="+1">'.
1.44 www 2433: &mt('Return').'</font></a>');
1.3 matthew 2434: }
1.76 albertel 2435: $r->print(&Apache::loncommon::end_page());
1.1 www 2436: return OK;
1.35 matthew 2437: }
2438:
2439: sub toggle_debug {
1.59 albertel 2440: if ($env{'user.debug'}) {
1.139 raeburn 2441: &Apache::lonnet::delenv('user.debug');
1.35 matthew 2442: } else {
1.116 raeburn 2443: &Apache::lonnet::appenv({'user.debug' => 1});
1.35 matthew 2444: }
1.13 www 2445: }
1.1 www 2446:
2447: 1;
2448: __END__
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>