Просмотр исходного кода

[php, js, css] change password is highly nice. checkbox fixes

naumov-socolov 14 лет назад
Родитель
Сommit
74c83ed412

+ 1 - 1
web/captcha.php

@@ -14,7 +14,7 @@ class Captcha
     protected $color3  = null; 
     protected $keyword = '';
     public    $key_len = 7;
-    protected $chars   = 'qw1e2r3t4y5u67o8p9as9d38f6g4h3j2k1l3z5x7c8v3b5n781234567890';
+    protected $chars   = 'qw1e2r3ty5u678p97as9d3o87f6gh3j2k73z5x7c8v3b75n77812356789';
     
     public function __construct()
     {

+ 41 - 60
web/change_password.php

@@ -13,6 +13,7 @@ require_once V_ROOT_DIR . 'core/exceptions/ProtectionException.class.php';
 require_once V_ROOT_DIR . 'core/utils/Message.class.php';
 require_once V_ROOT_DIR . 'core/Request.class.php';
 require_once V_ROOT_DIR . 'api/AjaxHandler.php';
+require_once V_ROOT_DIR . 'api/MAIN.class.php';
 
 
 class ChangePassword
@@ -26,14 +27,14 @@ class ChangePassword
         
         $key = addslashes(htmlspecialchars($_GET['v']));
 
-        $users = Vesta::execute(Vesta::V_LIST_SYS_USERS, 'json');
+        $cmd = Config::get('sudo_path')." ".Config::get('vesta_functions_path').Vesta::V_LIST_SYS_USERS." 'json'";
+        exec($cmd, $output, $return);
+ 
+        $users = json_decode(implode('', $output), true);
+
         $email_matched_count = array();
         
-        /*if (strcmp($real_key, $key_sha1) != 0) {
-            return $this->renderError('Invalid keys');      
-        }*/
-        
-        foreach ($users['data'] as $username => $user) {           
+        foreach ($users as $username => $user) {           
             if ($user['RKEY'] == trim($key)) {
                 $email_matched_count[] = array_merge(array('USERNAME' => $username), $user);
             }
@@ -62,15 +63,19 @@ class ChangePassword
         
         $success = true;
         foreach ($users as $user) {
-            $rs = Vesta::execute(Vesta::V_CHANGE_SYS_USER_PASSWORD, array('USER' => $user['USERNAME'], 
-                                                                             'PASSWORD' => $_POST['secret_code']));
-            if (!$rs) {
+            $cmd = Config::get('sudo_path')." ".Config::get('vesta_functions_path').Vesta::V_CHANGE_SYS_USER_PASSWORD." ".$user['USERNAME']." ".$_POST['secret_code'];
+            exec($cmd, $output, $return);
+
+            if (!$return) {
                 $success = false;
             }
         }
         
         if (!$success) {
-            return $this->showResetForm('Something went wrong. Please contact support.');
+            $main = new MAIN();
+            $about = json_decode($main->aboutExecute(), TRUE);
+    
+            return $this->showResetForm('Something went wrong. Please contact support: '.$about['data']['company_email']);
         }
         
         return $this->showSuccessTpl();
@@ -78,6 +83,10 @@ class ChangePassword
     
     public function showSuccessTpl()
     {
+        $main = new MAIN();
+        $about = json_decode($main->aboutExecute(), TRUE);
+        $current_year = date("Y");      
+
         print <<<HTML
 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
           <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ru">
@@ -101,7 +110,7 @@ class ChangePassword
                 <div class="b-auth-form">
                     <div class="b-auth-form-wrap">
                         <img width="72" height="24" alt="" src="/images/vesta-logo-2011-12-14.png" class="vesta-logo">
-            <span style="color: #5E696B; float: right; margin-top: -48px;">~!:VERSION~!</span>
+            <span style="color: #5E696B; float: right; margin-top: -48px;">{$about['data']['version_name']}</span>
                         <div class="b-client-title">
             <span class="client-title-wrap">Control Panel<i class="planets">&nbsp;</i></span>
                         </div>
@@ -111,10 +120,10 @@ class ChangePassword
                             <div class="success-box" id="change-psw-success">Password successfully changed.</div>
 
                         </form>
-                        <p class="forgot-pwd">&nbsp;</p>
+                        <p class="forgot-pwd"><a href="/" class="forgot-pwd-url">Back to login?</a></p>
                         <div class="footnotes cc">
-                        <p class="additional-info">For questions please contact <a href="mailto:info@vestacp.com" class="questions-url">info@vestacp.com</a></p>
-                        <address class="imprint">&copy; 2011 Vesta Control Panel</address>
+                        <p class="additional-info">For questions please contact <a href="mailto:{$about['data']['company_email']}" class="questions-url">{$about['data']['company_email']}</a></p> 
+                        <address class="imprint">&copy; {$current_year} Vesta Control Panel</address>
                         </div>
                     </div>
                  </div>
@@ -129,9 +138,14 @@ HTML;
     public function showResetForm($error_msg = '')
     {
         if (!empty($error_msg)) {
-            $error_msg = '<i>'.$error_msg.'</i>';
+            $error_msg = '<div class="error-box" id="auth-error">'.$error_msg.'</div>';
         }
-        
+
+        $main = new MAIN();
+        $about = json_decode($main->aboutExecute(), TRUE);
+
+        $current_year = date("Y");      
+
         print <<<HTML
 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
           <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ru">
@@ -154,13 +168,15 @@ HTML;
             <div id="change-psw-block" class="page2">
                 <div class="b-auth-form">
                     <div class="b-auth-form-wrap">
+                        <a href="/">
                         <img width="72" height="24" alt="" src="/images/vesta-logo-2011-12-14.png" class="vesta-logo">
-            <span style="color: #5E696B; float: right; margin-top: -48px;">~!:VERSION~!</span>
+                        </a>
+          <span style="color: #5E696B; float: right; margin-top: -48px;">{$about['data']['version_name']}</span>
                         <div class="b-client-title">
             <span class="client-title-wrap">Control Panel<i class="planets">&nbsp;</i></span>
                         </div>
                         <form id="change_psw-form" method="post" action="" class="auth">
-                <input type="hidden" value="change" name="action">
+                        <input type="hidden" value="change" name="action">
 
                             <div class="form-row cc">
                                 <label for="password" class="field-label">New Password</label>
@@ -171,58 +187,24 @@ HTML;
                                 <label for="confirm_password" class="field-label">ONE MORE TIME</label>
                                 <input type="password" tabindex="1" id="confirm_password" class="field-text" name="confirm_secret_code">
                             </div>
-
+                            {$error_msg}
                             <div class="form-row cc last-row">
                                 <input type="submit" tabindex="4" value="Change Password" class="sumbit-btn">
                             </div>
                         </form>
-                        <p class="forgot-pwd">&nbsp;</p>
+
+                        <p class="forgot-pwd"><a href="/" class="forgot-pwd-url">Back to login?</a></p>\
+
                         <div class="footnotes cc">
-                        <p class="additional-info">For questions please contact <a href="mailto:info@vestacp.com" class="questions-url">info@vestacp.com</a></p>
-                        <address class="imprint">&copy; 2011 Vesta Control Panel</address>
+                        <p class="additional-info">For questions please contact <a href="mailto:{$about['data']['company_email']}" class="questions-url">{$about['data']['company_email']}</a></p>
+                        <address class="imprint">&copy; {$current_year} Vesta Control Panel</address>
                         </div>
                     </div>
                  </div>
             </div>
     </body>
 </html>
-
-<!--
-
-            <center>
-            vesta password reset form 
-            <hr />
-            {$error_msg}
-            <form action="" method="POST">
-                <table>
-                    <tr>
-                        <td>
-                            <input type="hidden" name="action" value="change" />
-                            <label>Enter secret code:</label>
-                        </td>
-                        <td>
-                            <input type="password" name="secret_code" value="" />
-                        </td>
-                    </tr>
-                    <tr>
-                        <td>
-                            <label>Enter new password:</label>
-                        </td>
-                        <td>
-                            <input type="password" name="confirm_secret_code" value="" />
-                        </td>
-                    </tr>
-                    <tr>
-                        <td colspan="2">
-                            <input type="submit" name="Apply" />
-                        </td>
-                    </tr>
-                </table>
-            </form>
-            </center> --> 
-
 HTML;
-
     }
     
     public function renderError($message)
@@ -232,10 +214,9 @@ HTML;
 HTML;
     
     }
-
 }
 
 $changePassword = new ChangePassword();
 $changePassword->dispatch();
 
-?>
+?>

+ 13 - 3
web/css/main.css

@@ -591,8 +591,8 @@ input::-moz-focus-inner{
 	}
 	.checkbox-selector span.ui-checkbox{
 		float:none;
-		width:11px;
-		height:11px;
+		width:10px;
+		height:10px;
 		margin:2px 2px 0 0;
 		/*background:url(../i/checkbox-selector-2012-01-29.png) no-repeat;*/
 		background:url(../images/checkbox-selector-2012-01-31.png) no-repeat;
@@ -608,12 +608,16 @@ input::-moz-focus-inner{
 	}
 	.checkbox-selector span.ui-checkbox-hover{
 		background-position:0 -20px;
+    	-moz-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
+		-webkit-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
 	}
 	.checkbox-selector span.ui-checkbox-state-checked{
 		background-position:0 -40px;
 	}
 	.checkbox-selector span.ui-checkbox-state-checked-hover{
 		background-position:0 -60px;
+    	-moz-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
+		-webkit-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
 	}
 	.checkbox-selector .selector-title:hover{
 		color:#2ea8bd;	
@@ -1277,6 +1281,8 @@ input::-moz-focus-inner{
 		.row-actions-box .check-control:hover{
 			cursor:pointer;
 			background-position:0 -89px;
+        	-moz-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
+        	-webkit-box-shadow:0 0 5px rgba(82, 168, 236, 0.6);
 		}		
 		.row-actions-box .row-operations{
 			float:right;
@@ -1681,7 +1687,7 @@ input::-moz-focus-inner{
 		float:left;
 		width:18px;
 		height:18px;
-		margin:6px 0 0;
+		margin:9px 0 0;
 		/*background:url(../i/checkbox-1.png) no-repeat;*/
 		/*background:url(../i/form-checkboxes.png) no-repeat;*/
 		background:url(../images/checkbox-selector-2012-01-31.png) no-repeat -12px 0;
@@ -1691,12 +1697,16 @@ input::-moz-focus-inner{
 	}
 	.b-new-entry span.ui-checkbox-hover{
 		background-position:-12px -20px;
+    	-moz-box-shadow:0 0 8px rgba(82, 168, 236, 0.6);
+		-webkit-box-shadow:0 0 8px rgba(82, 168, 236, 0.6);
 	}	
 	.b-new-entry span.ui-checkbox-state-checked{
 		background-position:-12px -40px;
 	}	
 	.b-new-entry span.ui-checkbox-state-checked-hover{
 		background-position:-12px -60px;
+    	-moz-box-shadow:0 0 8px rgba(82, 168, 236, 0.6);
+		-webkit-box-shadow:0 0 8px rgba(82, 168, 236, 0.6);
 	}
 	
 	.b-new-entry .stats-settings{

+ 1 - 1
web/index.html

@@ -275,7 +275,7 @@
         <script type="text/javascript" src="js/pages.js"></script>
         <script type="text/javascript" src="js/model.js"></script>
         <script type="text/javascript" src="js/core.js"></script>
-        <script type="text/javascript" src="js/validators.js"></script>        
+        <script type="text/javascript" src="js/validators.js"></script>
         <script type="text/javascript" src="js/__init__.js"></script>
     </body>
 </html>

+ 4 - 2
web/js/actions.js

@@ -143,9 +143,8 @@ App.Actions.reset_batch = function()
 
 App.Actions.do_change_password = function()
 {
-    
     var params = {
-        email: $('#change-email').val(),
+        login: $('#change-login').val(),
         captcha: $('#captcha').val()
     }
     
@@ -261,11 +260,13 @@ App.Actions.new_entry = function() {
         var build_method = App.Env.getWorldName() + '_form';
         var tpl = App.HTML.Build[build_method]({}, form_id);
         var box = $('<div>').html(tpl);
+
         $(box).find('.suspended').addClass('hidden');
         App.Ref.CONTENT.prepend($(box).html());
         
         App.Helpers.updateScreen();
     }
+    $('.cust-checkbox').checkBox();
 }
 
 // execute authorisation
@@ -403,6 +404,7 @@ App.Actions.edit = function(evt)
         App.Helpers.disableNotEditable();
         App.Helpers.updateScreen();
     }
+    $('.cust-checkbox').checkBox();
 }
 
 // do_cancel_form

+ 1 - 2
web/js/html.js

@@ -43,7 +43,7 @@ App.HTML.Build.dns_form = function (options, id) {
     tpl.set(':DATE', options.DATE || '');
     tpl = App.HTML.Build.dns_selects(tpl, options);
     tpl = App.HTML.toggle_suspended_form(tpl, options);
-    
+
     return tpl.finalize();
 }
 
@@ -218,7 +218,6 @@ App.HTML.Build.web_domain_form = function (options, id) {
 
     tpl.set(':DNS_DOMAIN_ALSO', in_edit? 'hidden' : '');
 
-
     return tpl.finalize();
 }
 

+ 236 - 236
web/js/lib/jquery.ui.widget.js

@@ -1,236 +1,236 @@
-/*!
- * jQuery UI Widget 1.8
- *
- * Copyright (c) 2010 AUTHORS.txt (http://jqueryui.com/about)
- * Dual licensed under the MIT (MIT-LICENSE.txt)
- * and GPL (GPL-LICENSE.txt) licenses.
- *
- * http://docs.jquery.com/UI/Widget
- */
-(function( $ ) {
-
-var _remove = $.fn.remove;
-
-$.fn.remove = function( selector, keepData ) {
-	return this.each(function() {
-		if ( !keepData ) {
-			if ( !selector || $.filter( selector, [ this ] ).length ) {
-				$( "*", this ).add( this ).each(function() {
-					$( this ).triggerHandler( "remove" );
-				});
-			}
-		}
-		return _remove.call( $(this), selector, keepData );
-	});
-};
-
-$.widget = function( name, base, prototype ) {
-	var namespace = name.split( "." )[ 0 ],
-		fullName;
-	name = name.split( "." )[ 1 ];
-	fullName = namespace + "-" + name;
-
-	if ( !prototype ) {
-		prototype = base;
-		base = $.Widget;
-	}
-
-	// create selector for plugin
-	$.expr[ ":" ][ fullName ] = function( elem ) {
-		return !!$.data( elem, name );
-	};
-
-	$[ namespace ] = $[ namespace ] || {};
-	$[ namespace ][ name ] = function( options, element ) {
-		// allow instantiation without initializing for simple inheritance
-		if ( arguments.length ) {
-			this._createWidget( options, element );
-		}
-	};
-
-	var basePrototype = new base();
-	// we need to make the options hash a property directly on the new instance
-	// otherwise we'll modify the options hash on the prototype that we're
-	// inheriting from
-//	$.each( basePrototype, function( key, val ) {
-//		if ( $.isPlainObject(val) ) {
-//			basePrototype[ key ] = $.extend( {}, val );
-//		}
-//	});
-	basePrototype.options = $.extend( {}, basePrototype.options );
-	$[ namespace ][ name ].prototype = $.extend( true, basePrototype, {
-		namespace: namespace,
-		widgetName: name,
-		widgetEventPrefix: $[ namespace ][ name ].prototype.widgetEventPrefix || name,
-		widgetBaseClass: fullName
-	}, prototype );
-
-	$.widget.bridge( name, $[ namespace ][ name ] );
-};
-
-$.widget.bridge = function( name, object ) {
-	$.fn[ name ] = function( options ) {
-		var isMethodCall = typeof options === "string",
-			args = Array.prototype.slice.call( arguments, 1 ),
-			returnValue = this;
-
-		// allow multiple hashes to be passed on init
-		options = !isMethodCall && args.length ?
-			$.extend.apply( null, [ true, options ].concat(args) ) :
-			options;
-
-		// prevent calls to internal methods
-		if ( isMethodCall && options.substring( 0, 1 ) === "_" ) {
-			return returnValue;
-		}
-
-		if ( isMethodCall ) {
-			this.each(function() {
-				var instance = $.data( this, name ),
-					methodValue = instance && $.isFunction( instance[options] ) ?
-						instance[ options ].apply( instance, args ) :
-						instance;
-				if ( methodValue !== instance && methodValue !== undefined ) {
-					returnValue = methodValue;
-					return false;
-				}
-			});
-		} else {
-			this.each(function() {
-				var instance = $.data( this, name );
-				if ( instance ) {
-					if ( options ) {
-						instance.option( options );
-					}
-					instance._init();
-				} else {
-					$.data( this, name, new object( options, this ) );
-				}
-			});
-		}
-
-		return returnValue;
-	};
-};
-
-$.Widget = function( options, element ) {
-	// allow instantiation without initializing for simple inheritance
-	if ( arguments.length ) {
-		this._createWidget( options, element );
-	}
-};
-
-$.Widget.prototype = {
-	widgetName: "widget",
-	widgetEventPrefix: "",
-	options: {
-		disabled: false
-	},
-	_createWidget: function( options, element ) {
-		// $.widget.bridge stores the plugin instance, but we do it anyway
-		// so that it's stored even before the _create function runs
-		this.element = $( element ).data( this.widgetName, this );
-		this.options = $.extend( true, {},
-			this.options,
-			$.metadata && $.metadata.get( element )[ this.widgetName ],
-			options );
-
-		var self = this;
-		this.element.bind( "remove." + this.widgetName, function() {
-			self.destroy();
-		});
-
-		this._create();
-		this._init();
-	},
-	_create: function() {},
-	_init: function() {},
-
-	destroy: function() {
-		this.element
-			.unbind( "." + this.widgetName )
-			.removeData( this.widgetName );
-		this.widget()
-			.unbind( "." + this.widgetName )
-			.removeAttr( "aria-disabled" )
-			.removeClass(
-				this.widgetBaseClass + "-disabled " +
-				this.namespace + "-state-disabled" );
-	},
-
-	widget: function() {
-		return this.element;
-	},
-
-	option: function( key, value ) {
-		var options = key,
-			self = this;
-
-		if ( arguments.length === 0 ) {
-			// don't return a reference to the internal hash
-			return $.extend( {}, self.options );
-		}
-
-		if  (typeof key === "string" ) {
-			if ( value === undefined ) {
-				return this.options[ key ];
-			}
-			options = {};
-			options[ key ] = value;
-		}
-
-		$.each( options, function( key, value ) {
-			self._setOption( key, value );
-		});
-
-		return self;
-	},
-	_setOption: function( key, value ) {
-		this.options[ key ] = value;
-
-		if ( key === "disabled" ) {
-			this.widget()
-				[ value ? "addClass" : "removeClass"](
-					this.widgetBaseClass + "-disabled" + " " +
-					this.namespace + "-state-disabled" )
-				.attr( "aria-disabled", value );
-		}
-
-		return this;
-	},
-
-	enable: function() {
-		return this._setOption( "disabled", false );
-	},
-	disable: function() {
-		return this._setOption( "disabled", true );
-	},
-
-	_trigger: function( type, event, data ) {
-		var callback = this.options[ type ];
-
-		event = $.Event( event );
-		event.type = ( type === this.widgetEventPrefix ?
-			type :
-			this.widgetEventPrefix + type ).toLowerCase();
-		data = data || {};
-
-		// copy original event properties over to the new event
-		// this would happen if we could call $.event.fix instead of $.Event
-		// but we don't have a way to force an event to be fixed multiple times
-		if ( event.originalEvent ) {
-			for ( var i = $.event.props.length, prop; i; ) {
-				prop = $.event.props[ --i ];
-				event[ prop ] = event.originalEvent[ prop ];
-			}
-		}
-
-		this.element.trigger( event, data );
-
-		return !( $.isFunction(callback) &&
-			callback.call( this.element[0], event, data ) === false ||
-			event.isDefaultPrevented() );
-	}
-};
-
-})( jQuery );
+/*!
+ * jQuery UI Widget 1.8
+ *
+ * Copyright (c) 2010 AUTHORS.txt (http://jqueryui.com/about)
+ * Dual licensed under the MIT (MIT-LICENSE.txt)
+ * and GPL (GPL-LICENSE.txt) licenses.
+ *
+ * http://docs.jquery.com/UI/Widget
+ */
+(function( $ ) {
+
+var _remove = $.fn.remove;
+
+$.fn.remove = function( selector, keepData ) {
+	return this.each(function() {
+		if ( !keepData ) {
+			if ( !selector || $.filter( selector, [ this ] ).length ) {
+				$( "*", this ).add( this ).each(function() {
+					$( this ).triggerHandler( "remove" );
+				});
+			}
+		}
+		return _remove.call( $(this), selector, keepData );
+	});
+};
+
+$.widget = function( name, base, prototype ) {
+	var namespace = name.split( "." )[ 0 ],
+		fullName;
+	name = name.split( "." )[ 1 ];
+	fullName = namespace + "-" + name;
+
+	if ( !prototype ) {
+		prototype = base;
+		base = $.Widget;
+	}
+
+	// create selector for plugin
+	$.expr[ ":" ][ fullName ] = function( elem ) {
+		return !!$.data( elem, name );
+	};
+
+	$[ namespace ] = $[ namespace ] || {};
+	$[ namespace ][ name ] = function( options, element ) {
+		// allow instantiation without initializing for simple inheritance
+		if ( arguments.length ) {
+			this._createWidget( options, element );
+		}
+	};
+
+	var basePrototype = new base();
+	// we need to make the options hash a property directly on the new instance
+	// otherwise we'll modify the options hash on the prototype that we're
+	// inheriting from
+//	$.each( basePrototype, function( key, val ) {
+//		if ( $.isPlainObject(val) ) {
+//			basePrototype[ key ] = $.extend( {}, val );
+//		}
+//	});
+	basePrototype.options = $.extend( {}, basePrototype.options );
+	$[ namespace ][ name ].prototype = $.extend( true, basePrototype, {
+		namespace: namespace,
+		widgetName: name,
+		widgetEventPrefix: $[ namespace ][ name ].prototype.widgetEventPrefix || name,
+		widgetBaseClass: fullName
+	}, prototype );
+
+	$.widget.bridge( name, $[ namespace ][ name ] );
+};
+
+$.widget.bridge = function( name, object ) {
+	$.fn[ name ] = function( options ) {
+		var isMethodCall = typeof options === "string",
+			args = Array.prototype.slice.call( arguments, 1 ),
+			returnValue = this;
+
+		// allow multiple hashes to be passed on init
+		options = !isMethodCall && args.length ?
+			$.extend.apply( null, [ true, options ].concat(args) ) :
+			options;
+
+		// prevent calls to internal methods
+		if ( isMethodCall && options.substring( 0, 1 ) === "_" ) {
+			return returnValue;
+		}
+
+		if ( isMethodCall ) {
+			this.each(function() {
+				var instance = $.data( this, name ),
+					methodValue = instance && $.isFunction( instance[options] ) ?
+						instance[ options ].apply( instance, args ) :
+						instance;
+				if ( methodValue !== instance && methodValue !== undefined ) {
+					returnValue = methodValue;
+					return false;
+				}
+			});
+		} else {
+			this.each(function() {
+				var instance = $.data( this, name );
+				if ( instance ) {
+					if ( options ) {
+						instance.option( options );
+					}
+					instance._init();
+				} else {
+					$.data( this, name, new object( options, this ) );
+				}
+			});
+		}
+
+		return returnValue;
+	};
+};
+
+$.Widget = function( options, element ) {
+	// allow instantiation without initializing for simple inheritance
+	if ( arguments.length ) {
+		this._createWidget( options, element );
+	}
+};
+
+$.Widget.prototype = {
+	widgetName: "widget",
+	widgetEventPrefix: "",
+	options: {
+		disabled: false
+	},
+	_createWidget: function( options, element ) {
+		// $.widget.bridge stores the plugin instance, but we do it anyway
+		// so that it's stored even before the _create function runs
+		this.element = $( element ).data( this.widgetName, this );
+		this.options = $.extend( true, {},
+			this.options,
+			$.metadata && $.metadata.get( element )[ this.widgetName ],
+			options );
+
+		var self = this;
+		this.element.bind( "remove." + this.widgetName, function() {
+			self.destroy();
+		});
+
+		this._create();
+		this._init();
+	},
+	_create: function() {},
+	_init: function() {},
+
+	destroy: function() {
+		this.element
+			.unbind( "." + this.widgetName )
+			.removeData( this.widgetName );
+		this.widget()
+			.unbind( "." + this.widgetName )
+			.removeAttr( "aria-disabled" )
+			.removeClass(
+				this.widgetBaseClass + "-disabled " +
+				this.namespace + "-state-disabled" );
+	},
+
+	widget: function() {
+		return this.element;
+	},
+
+	option: function( key, value ) {
+		var options = key,
+			self = this;
+
+		if ( arguments.length === 0 ) {
+			// don't return a reference to the internal hash
+			return $.extend( {}, self.options );
+		}
+
+		if  (typeof key === "string" ) {
+			if ( value === undefined ) {
+				return this.options[ key ];
+			}
+			options = {};
+			options[ key ] = value;
+		}
+
+		$.each( options, function( key, value ) {
+			self._setOption( key, value );
+		});
+
+		return self;
+	},
+	_setOption: function( key, value ) {
+		this.options[ key ] = value;
+
+		if ( key === "disabled" ) {
+			this.widget()
+				[ value ? "addClass" : "removeClass"](
+					this.widgetBaseClass + "-disabled" + " " +
+					this.namespace + "-state-disabled" )
+				.attr( "aria-disabled", value );
+		}
+
+		return this;
+	},
+
+	enable: function() {
+		return this._setOption( "disabled", false );
+	},
+	disable: function() {
+		return this._setOption( "disabled", true );
+	},
+
+	_trigger: function( type, event, data ) {
+		var callback = this.options[ type ];
+
+		event = $.Event( event );
+		event.type = ( type === this.widgetEventPrefix ?
+			type :
+			this.widgetEventPrefix + type ).toLowerCase();
+		data = data || {};
+
+		// copy original event properties over to the new event
+		// this would happen if we could call $.event.fix instead of $.Event
+		// but we don't have a way to force an event to be fixed multiple times
+		if ( event.originalEvent ) {
+			for ( var i = $.event.props.length, prop; i; ) {
+				prop = $.event.props[ --i ];
+				event[ prop ] = event.originalEvent[ prop ];
+			}
+		}
+
+		this.element.trigger( event, data );
+
+		return !( $.isFunction(callback) &&
+			callback.call( this.element[0], event, data ) === false ||
+			event.isDefaultPrevented() );
+	}
+};
+
+})( jQuery );

+ 75 - 75
web/js/lib/jquery.usermode.js

@@ -1,75 +1,75 @@
-/**
- * @author trixta
- */
-(function($){
-	$.userMode = (function(){
-		var userBg, 
-			timer, 
-			testDiv,
-			boundEvents = 0;
-		
-		function testBg(){
-			testDiv = testDiv || $('<div></div>').css({position: 'absolute', left: '-999em', top: '-999px', width: '0px', height: '0px'}).appendTo('body');
-			var black = $.curCSS( testDiv.css({backgroundColor: '#000000'})[0], 'backgroundColor', true),
-				white = $.curCSS( testDiv.css({backgroundColor: '#ffffff'})[0], 'backgroundColor', true),
-				newBgStatus = (black === white || white === 'transparent');
-			if(newBgStatus != userBg){
-				userBg = newBgStatus;
-				$.event.trigger('_internalusermode');
-			}
-			return userBg;
-		}
-		
-		function init(){
-			testBg();
-			timer = setInterval(testBg, 3000);
-		}
-		
-		function stop(){
-			clearInterval(timer);
-			testDiv.remove();
-			testDiv = null;
-		}
-		
-		$.event.special.usermode = {
-			setup: function(){
-				(!boundEvents && init());
-				boundEvents++;
-				var jElem = $(this)
-					.bind('_internalusermode', $.event.special.usermode.handler);
-				//always trigger
-				setTimeout(function(){
-					jElem.triggerHandler('_internalusermode');
-				}, 1);
-                return true;
-            },
-			teardown: function(){
-                boundEvents--;
-				(!boundEvents && stop());
-				$(this).unbind('_internalusermode', $.event.special.usermode.handler);
-                return true;
-            },
-            handler: function(e){
-                e.type = 'usermode';
-				e.disabled = !userBg;
-				e.enabled = userBg;
-                return jQuery.event.handle.apply(this, arguments);
-            }
-		};
-		
-		return {
-			get: testBg
-		};
-		
-	})();
-	
-	$.fn.userMode = function(fn){
-		return this[(fn) ? 'bind' : 'trigger']('usermode', fn);
-	};
-	
-	$(function(){
-		$('html').userMode(function(e){
-			$('html')[e.enabled ? 'addClass' : 'removeClass']('hcm');
-		});
-	});
-})(jQuery);
+/**
+ * @author trixta
+ */
+(function($){
+	$.userMode = (function(){
+		var userBg, 
+			timer, 
+			testDiv,
+			boundEvents = 0;
+		
+		function testBg(){
+			testDiv = testDiv || $('<div></div>').css({position: 'absolute', left: '-999em', top: '-999px', width: '0px', height: '0px'}).appendTo('body');
+			var black = $.curCSS( testDiv.css({backgroundColor: '#000000'})[0], 'backgroundColor', true),
+				white = $.curCSS( testDiv.css({backgroundColor: '#ffffff'})[0], 'backgroundColor', true),
+				newBgStatus = (black === white || white === 'transparent');
+			if(newBgStatus != userBg){
+				userBg = newBgStatus;
+				$.event.trigger('_internalusermode');
+			}
+			return userBg;
+		}
+		
+		function init(){
+			testBg();
+			timer = setInterval(testBg, 3000);
+		}
+		
+		function stop(){
+			clearInterval(timer);
+			testDiv.remove();
+			testDiv = null;
+		}
+		
+		$.event.special.usermode = {
+			setup: function(){
+				(!boundEvents && init());
+				boundEvents++;
+				var jElem = $(this)
+					.bind('_internalusermode', $.event.special.usermode.handler);
+				//always trigger
+				setTimeout(function(){
+					jElem.triggerHandler('_internalusermode');
+				}, 1);
+                return true;
+            },
+			teardown: function(){
+                boundEvents--;
+				(!boundEvents && stop());
+				$(this).unbind('_internalusermode', $.event.special.usermode.handler);
+                return true;
+            },
+            handler: function(e){
+                e.type = 'usermode';
+				e.disabled = !userBg;
+				e.enabled = userBg;
+                return jQuery.event.handle.apply(this, arguments);
+            }
+		};
+		
+		return {
+			get: testBg
+		};
+		
+	})();
+	
+	$.fn.userMode = function(fn){
+		return this[(fn) ? 'bind' : 'trigger']('usermode', fn);
+	};
+	
+	$(function(){
+		$('html').userMode(function(e){
+			$('html')[e.enabled ? 'addClass' : 'removeClass']('hcm');
+		});
+	});
+})(jQuery);

+ 276 - 276
web/js/lib/ui.checkbox.js

@@ -1,276 +1,276 @@
-/**
- * @author alexander.farkas
- * @version 1.4.3
- */
-(function($){
-	
-	var supportsValidity;
-	(function(){
-		if(!$.prop || supportsValidity){return;}
-		var supportTest = function(){
-			supportsValidity = !!$('<input />').prop('validity');
-		};
-		supportTest();
-		$(supportTest);
-	})();
-	
-    $.widget('ui.checkBox', {
-		options: {
-	        hideInput: true,
-			addVisualElement: true,
-			addLabel: true
-	    },
-        _create: function(){
-            var that = this, 
-				opts = this.options
-			;
-			
-			if(!this.element.is(':radio,:checkbox')){
-				if(this.element[0].elements && $.nodeName(this.element[0], 'form')){
-					$(this.element[0].elements).filter(':radio,:checkbox').checkBox(opts);
-				}
-				return false;
-			}
-			
-			this._proxiedReflectUI = $.proxy(this, 'reflectUI');
-			
-            this.labels = $([]);
-			
-            this.checkedStatus = false;
-			this.disabledStatus = false;
-			this.hoverStatus = false;
-            
-			this.inputType = this.element[0].type;
-            this.radio = this.inputType == 'radio';
-					
-            this.visualElement = $([]);
-            if (opts.hideInput) {
-				this.element.addClass('ui-helper-hidden-accessible');
-				if(opts.addVisualElement){
-					this.visualElement = $('<span />')
-						.addClass('ui-'+this.inputType)
-					;
-					this.element.after(this.visualElement[0]);
-				}
-            }
-			
-			if(opts.addLabel){
-				var id = this.element[0].id;
-				if(id){
-					this.labels = $('label[for="' + id + '"]', this.element[0].form || this.element[0].ownerDocument).add(this.element.parent('label'));
-				}
-				if(!this.labels[0]){
-					this.labels = this.element.closest('label', this.element[0].form);
-				}
-				this.labels.addClass(this.radio ? 'ui-radio' : 'ui-checkbox');
-			}
-			
-			this.visualGroup = this.visualElement.add(this.labels);
-			
-			this._addEvents();
-			
-			this.initialized = true;
-            this.reflectUI({type: 'initialreflect'});
-			return undefined;
-        },
-		_addEvents: function(){
-			var that 		= this, 
-			
-				opts 		= this.options,
-					
-				toggleHover = function(e){
-					if(that.disabledStatus){
-						return false;
-					}
-					that.hover = (e.type == 'focus' || e.type == 'mouseenter');
-					if(e.type == 'focus'){
-						that.visualGroup.addClass(that.inputType +'-focused');
-					} else if(e.type == 'blur'){
-						that.visualGroup.removeClass(that.inputType +'-focused');
-					}
-					that._changeStateClassChain();
-					return undefined;
-				}
-			;
-			
-			this.element
-				.bind('click.checkBox invalid.checkBox', this._proxiedReflectUI)
-				.bind('focus.checkBox blur.checkBox', toggleHover)
-			;
-			if (opts.hideInput){
-				this.element
-					.bind('usermode', function(e){
-	                    (e.enabled &&
-	                        that.destroy.call(that, true));
-	                })
-				;
-            }
-			if(opts.addVisualElement){
-				this.visualElement
-					.bind('click.checkBox', function(e){
-						that.element[0].click();
-						return false;
-					})
-				;
-			}
-			
-			this.visualGroup.bind('mouseenter.checkBox mouseleave.checkBox', toggleHover);
-			
-		},
-		_changeStateClassChain: function(){
-			var allElements = this.labels.add(this.visualElement),
-				stateClass 	= '',
-				baseClass 	= 'ui-'+ this.inputType
-			;
-				
-			if(this.checkedStatus){
-				stateClass += '-checked'; 
-				allElements.addClass(baseClass+'-checked');
-			} else {
-				allElements.removeClass(baseClass+'-checked');
-			}
-			
-			if(this.disabledStatus){
-				stateClass += '-disabled'; 
-				allElements.addClass(baseClass+'-disabled');
-			} else {
-				allElements.removeClass(baseClass+'-disabled');
-			}
-			if(this.hover){
-				stateClass += '-hover'; 
-				allElements.addClass(baseClass+'-hover');
-			} else {
-				allElements.removeClass(baseClass+'-hover');
-			}
-			
-			baseClass += '-state';
-			if(stateClass){
-				stateClass = baseClass + stateClass;
-			}
-			
-			function switchStateClass(){
-				var classes = this.className.split(' '),
-					found = false;
-				$.each(classes, function(i, classN){
-					if(classN.indexOf(baseClass) === 0){
-						found = true;
-						classes[i] = stateClass;
-						return false;
-					}
-					return undefined;
-				});
-				if(!found){
-					classes.push(stateClass);
-				}
-				this.className = classes.join(' ');
-			}
-			
-			this.visualGroup.each(switchStateClass);
-		},
-        destroy: function(onlyCss){
-            this.element.removeClass('ui-helper-hidden-accessible');
-			this.visualElement.addClass('ui-helper-hidden');
-            if (!onlyCss) {
-                var o = this.options;
-                this.element.unbind('.checkBox');
-				this.visualElement.remove();
-                this.labels
-					.unbind('.checkBox')
-					.removeClass('ui-state-hover ui-state-checked ui-state-disabled')
-				;
-            }
-        },
-		
-        disable: function(status){
-			if(status === undefined){
-				status = true;
-			}
-            this.element[0].disabled = status;
-            this.reflectUI({type: 'manuallydisabled'});
-        },
-		
-        enable: function(){
-            this.element[0].disabled = false;
-            this.reflectUI({type: 'manuallyenabled'});
-        },
-		
-        toggle: function(e){
-            this.changeCheckStatus(!(this.element.is(':checked')), e);
-        },
-		
-        changeCheckStatus: function(status, e){
-            if(e && e.type == 'click' && this.element[0].disabled){
-				return false;
-			}
-			this.element[0].checked = !!status;
-            this.reflectUI(e || {
-                type: 'changecheckstatus'
-            });
-			return undefined;
-        },
-        propagate: function(n, e, _noGroupReflect){
-			if(!e || e.type != 'initialreflect'){
-				if (this.radio && !_noGroupReflect) {
-					var elem = this.element[0];
-					//dynamic
-	                $('[name="'+ elem.name +'"]', elem.form || elem.ownerDocument).checkBox('reflectUI', e, true);
-						
-	            }
-	            return this._trigger(n, e, {
-	                options: this.options,
-	                checked: this.checkedStatus,
-	                labels: this.labels,
-					disabled: this.disabledStatus
-	            });
-			}
-			return undefined;
-        },
-		changeValidityState: function(){
-			if(supportsValidity){
-				this.visualGroup[ !this.element.prop('willValidate') || (this.element.prop('validity') || {valid: true}).valid ? 'removeClass' : 'addClass' ](this.inputType +'-invalid');
-			}
-		},
-        reflectUI: function(e){
-			
-            var oldChecked 			= this.checkedStatus, 
-				oldDisabledStatus 	= this.disabledStatus
-			;
-            					
-			this.disabledStatus = this.element.is(':disabled');
-			this.checkedStatus = this.element.is(':checked');
-			if(!e || e.type !== 'initialreflect'){
-				this.changeValidityState();
-			}
-			
-			if (this.disabledStatus != oldDisabledStatus || this.checkedStatus !== oldChecked) {
-				this._changeStateClassChain();
-				
-				(this.disabledStatus != oldDisabledStatus &&
-					this.propagate('disabledchange', e));
-				
-				(this.checkedStatus !== oldChecked &&
-					this.propagate('change', e));
-			}
-            
-        }
-    });
-		
-	if($.propHooks){
-		$.each({checked: 'changeCheckStatus', disabled: 'disable'}, function(name, fn){
-			//be hook friendly
-			if(!$.propHooks[name]){
-				$.propHooks[name] = {};
-			}
-			var oldSetHook = $.propHooks[name].set;
-			
-			$.propHooks[name].set = function(elem, value){
-				var widget = $.data(elem, 'checkBox');
-				if(widget){
-					widget[fn](!!value);
-				}
-				return oldSetHook && oldSetHook(elem, value) ;
-			};
-			
-		});
-	}
-})(jQuery);
+/**
+ * @author alexander.farkas
+ * @version 1.4.3
+ */
+(function($){
+	
+	var supportsValidity;
+	(function(){
+		if(!$.prop || supportsValidity){return;}
+		var supportTest = function(){
+			supportsValidity = !!$('<input />').prop('validity');
+		};
+		supportTest();
+		$(supportTest);
+	})();
+	
+    $.widget('ui.checkBox', {
+		options: {
+	        hideInput: true,
+			addVisualElement: true,
+			addLabel: true
+	    },
+        _create: function(){
+            var that = this, 
+				opts = this.options
+			;
+			
+			if(!this.element.is(':radio,:checkbox')){
+				if(this.element[0].elements && $.nodeName(this.element[0], 'form')){
+					$(this.element[0].elements).filter(':radio,:checkbox').checkBox(opts);
+				}
+				return false;
+			}
+			
+			this._proxiedReflectUI = $.proxy(this, 'reflectUI');
+			
+            this.labels = $([]);
+			
+            this.checkedStatus = false;
+			this.disabledStatus = false;
+			this.hoverStatus = false;
+            
+			this.inputType = this.element[0].type;
+            this.radio = this.inputType == 'radio';
+					
+            this.visualElement = $([]);
+            if (opts.hideInput) {
+				this.element.addClass('ui-helper-hidden-accessible');
+				if(opts.addVisualElement){
+					this.visualElement = $('<span />')
+						.addClass('ui-'+this.inputType)
+					;
+					this.element.after(this.visualElement[0]);
+				}
+            }
+			
+			if(opts.addLabel){
+				var id = this.element[0].id;
+				if(id){
+					this.labels = $('label[for="' + id + '"]', this.element[0].form || this.element[0].ownerDocument).add(this.element.parent('label'));
+				}
+				if(!this.labels[0]){
+					this.labels = this.element.closest('label', this.element[0].form);
+				}
+				this.labels.addClass(this.radio ? 'ui-radio' : 'ui-checkbox');
+			}
+			
+			this.visualGroup = this.visualElement.add(this.labels);
+			
+			this._addEvents();
+			
+			this.initialized = true;
+            this.reflectUI({type: 'initialreflect'});
+			return undefined;
+        },
+		_addEvents: function(){
+			var that 		= this, 
+			
+				opts 		= this.options,
+					
+				toggleHover = function(e){
+					if(that.disabledStatus){
+						return false;
+					}
+					that.hover = (e.type == 'focus' || e.type == 'mouseenter');
+					if(e.type == 'focus'){
+						that.visualGroup.addClass(that.inputType +'-focused');
+					} else if(e.type == 'blur'){
+						that.visualGroup.removeClass(that.inputType +'-focused');
+					}
+					that._changeStateClassChain();
+					return undefined;
+				}
+			;
+			
+			this.element
+				.bind('click.checkBox invalid.checkBox', this._proxiedReflectUI)
+				.bind('focus.checkBox blur.checkBox', toggleHover)
+			;
+			if (opts.hideInput){
+				this.element
+					.bind('usermode', function(e){
+	                    (e.enabled &&
+	                        that.destroy.call(that, true));
+	                })
+				;
+            }
+			if(opts.addVisualElement){
+				this.visualElement
+					.bind('click.checkBox', function(e){
+						that.element[0].click();
+						return false;
+					})
+				;
+			}
+			
+			this.visualGroup.bind('mouseenter.checkBox mouseleave.checkBox', toggleHover);
+			
+		},
+		_changeStateClassChain: function(){
+			var allElements = this.labels.add(this.visualElement),
+				stateClass 	= '',
+				baseClass 	= 'ui-'+ this.inputType
+			;
+				
+			if(this.checkedStatus){
+				stateClass += '-checked'; 
+				allElements.addClass(baseClass+'-checked');
+			} else {
+				allElements.removeClass(baseClass+'-checked');
+			}
+			
+			if(this.disabledStatus){
+				stateClass += '-disabled'; 
+				allElements.addClass(baseClass+'-disabled');
+			} else {
+				allElements.removeClass(baseClass+'-disabled');
+			}
+			if(this.hover){
+				stateClass += '-hover'; 
+				allElements.addClass(baseClass+'-hover');
+			} else {
+				allElements.removeClass(baseClass+'-hover');
+			}
+			
+			baseClass += '-state';
+			if(stateClass){
+				stateClass = baseClass + stateClass;
+			}
+			
+			function switchStateClass(){
+				var classes = this.className.split(' '),
+					found = false;
+				$.each(classes, function(i, classN){
+					if(classN.indexOf(baseClass) === 0){
+						found = true;
+						classes[i] = stateClass;
+						return false;
+					}
+					return undefined;
+				});
+				if(!found){
+					classes.push(stateClass);
+				}
+				this.className = classes.join(' ');
+			}
+			
+			this.visualGroup.each(switchStateClass);
+		},
+        destroy: function(onlyCss){
+            this.element.removeClass('ui-helper-hidden-accessible');
+			this.visualElement.addClass('ui-helper-hidden');
+            if (!onlyCss) {
+                var o = this.options;
+                this.element.unbind('.checkBox');
+				this.visualElement.remove();
+                this.labels
+					.unbind('.checkBox')
+					.removeClass('ui-state-hover ui-state-checked ui-state-disabled')
+				;
+            }
+        },
+		
+        disable: function(status){
+			if(status === undefined){
+				status = true;
+			}
+            this.element[0].disabled = status;
+            this.reflectUI({type: 'manuallydisabled'});
+        },
+		
+        enable: function(){
+            this.element[0].disabled = false;
+            this.reflectUI({type: 'manuallyenabled'});
+        },
+		
+        toggle: function(e){
+            this.changeCheckStatus(!(this.element.is(':checked')), e);
+        },
+		
+        changeCheckStatus: function(status, e){
+            if(e && e.type == 'click' && this.element[0].disabled){
+				return false;
+			}
+			this.element[0].checked = !!status;
+            this.reflectUI(e || {
+                type: 'changecheckstatus'
+            });
+			return undefined;
+        },
+        propagate: function(n, e, _noGroupReflect){
+			if(!e || e.type != 'initialreflect'){
+				if (this.radio && !_noGroupReflect) {
+					var elem = this.element[0];
+					//dynamic
+	                $('[name="'+ elem.name +'"]', elem.form || elem.ownerDocument).checkBox('reflectUI', e, true);
+						
+	            }
+	            return this._trigger(n, e, {
+	                options: this.options,
+	                checked: this.checkedStatus,
+	                labels: this.labels,
+					disabled: this.disabledStatus
+	            });
+			}
+			return undefined;
+        },
+		changeValidityState: function(){
+			if(supportsValidity){
+				this.visualGroup[ !this.element.prop('willValidate') || (this.element.prop('validity') || {valid: true}).valid ? 'removeClass' : 'addClass' ](this.inputType +'-invalid');
+			}
+		},
+        reflectUI: function(e){
+			
+            var oldChecked 			= this.checkedStatus, 
+				oldDisabledStatus 	= this.disabledStatus
+			;
+            					
+			this.disabledStatus = this.element.is(':disabled');
+			this.checkedStatus = this.element.is(':checked');
+			if(!e || e.type !== 'initialreflect'){
+				this.changeValidityState();
+			}
+			
+			if (this.disabledStatus != oldDisabledStatus || this.checkedStatus !== oldChecked) {
+				this._changeStateClassChain();
+				
+				(this.disabledStatus != oldDisabledStatus &&
+					this.propagate('disabledchange', e));
+				
+				(this.checkedStatus !== oldChecked &&
+					this.propagate('change', e));
+			}
+            
+        }
+    });
+		
+	if($.propHooks){
+		$.each({checked: 'changeCheckStatus', disabled: 'disable'}, function(name, fn){
+			//be hook friendly
+			if(!$.propHooks[name]){
+				$.propHooks[name] = {};
+			}
+			var oldSetHook = $.propHooks[name].set;
+			
+			$.propHooks[name].set = function(elem, value){
+				var widget = $.data(elem, 'checkBox');
+				if(widget){
+					widget[fn](!!value);
+				}
+				return oldSetHook && oldSetHook(elem, value) ;
+			};
+			
+		});
+	}
+})(jQuery);

+ 8 - 4
web/js/templates.js

@@ -44,20 +44,22 @@ App.Templates.html = {
             '<div id="change-psw-block" class="page2">\
                 <div class="b-auth-form">\
                     <div class="b-auth-form-wrap">\
+                        <a href="/">\
                         <img width="72" height="24" alt="" src="~!:LOGO_URL~!" class="vesta-logo">\
+                        </a>\
                         <span style="color: #5E696B; float: right; margin-top: -48px;">~!:VERSION~!</span>\
                         <div class="b-client-title">\
                             <span class="client-title-wrap">~!:PRODUCT_NAME~!<i class="planets">&nbsp;</i></span>\
                         </div>\
                         <form id="change_psw-form" method="post" action="#" class="auth">\
                             <div class="form-row cc">\
-                                <label for="change-email" class="field-label">Email</label>\
-                                <input type="text" tabindex="1" id="change-email" class="field-text">\
+                                <label for="change-login" class="field-label">Login</label>\
+                                <input type="text" tabindex="1" id="change-login" class="field-text">\
                             </div>\
                             <div class="form-row cc">\
                                 <label for="captcha" class="field-label">Captcha</label>\
                                 <label class="captcha"><img id="captcha-img" width="127px;" src="~!:CAPTCHA_URL~!"  style="cursor: pointer; float: left; margin-top: -7px; padding-left: 20px;" onClick="this.src = \'~!:CAPTCHA_URL_2~!?\'+Math.floor(Math.random() * 9999)"/></label>\
-                                <input type="text" id="captcha" class="field-text" style="margin-left: 11px; width: 132px; margin-bottom: 27px;">\
+                                <input type="text" id="captcha" tabindex=2 class="field-text" style="margin-left: 11px; width: 132px; margin-bottom: 27px;">\
                             </div>\
                             <div id="change-psw-success" class="success-box hidden"></div>\
                             <div id="change-psw-error" class="error-box hidden"></div>\
@@ -65,7 +67,7 @@ App.Templates.html = {
                                 <div class="b-remember">\
                                     <span class="remember-me">&nbsp;</span>\
                                 </div>\
-                                <input type="submit" tabindex="4" value="Send confirmation" class="sumbit-btn do_action_do_change_password">\
+                                <input type="submit" tabindex="3" value="Send confirmation" class="sumbit-btn do_action_do_change_password">\
                             </div>\
                         </form>\
                         <p class="forgot-pwd"><a href="#" class="forgot-pwd-url do_action_back_to_login">Back to login?</a></p>\
@@ -80,7 +82,9 @@ App.Templates.html = {
         login: ['<div id="auth-block" class="page2">\
         <div class="b-auth-form">\
             <div class="b-auth-form-wrap">\
+                <a href="/">\
                 <img width="72" height="24" alt="" src="~!:LOGO_URL~!" class="vesta-logo">\
+                </a>\
                 <span style="color: #5E696B; float: right; margin-top: -48px;">~!:VERSION~!</span>\
                 <div class="b-client-title">\
                     <span class="client-title-wrap">~!:PRODUCT_NAME~!<i class="planets">&nbsp;</i></span>\

+ 2 - 2
web/js/ui.checkbox.init.js

@@ -1,3 +1,3 @@
-$(document).ready(function(){
-	$('.cust-checkbox').checkBox();
+$(document).ready(function(){
+	$('.cust-checkbox').checkBox();
 });

+ 9 - 9
web/js/user_templates.js

@@ -126,18 +126,18 @@ App.Templates.html = {
                     </div>\
                     <div class="form-row cc">\
                             <input type="hidden" value="~!:DATE~!" name="DATE">\
-                            <label for="#" class="field-label">Domain:</label>\
-                            <input type="text" name="DNS_DOMAIN" value="~!:DNS_DOMAIN~!" class="text-field rule-required rule-domain">\
+                            <label for="dns-domain" class="field-label"><span class="mandatory">Domain:</span></label>\
+                            <input type="text" id="dns-domain" name="DNS_DOMAIN" value="~!:DNS_DOMAIN~!" class="text-field rule-required rule-domain">\
                     </div>\
                     <div class="form-row cc">\
-                            <label for="#" class="field-label">IP:</label>\
+                            <label for="ip" class="field-label"><span class="mandatory">IP:</span></label>\
                             <div class="autocomplete-box">\
-                                    <input type="text" name="IP" value="~!:IP~!" class="text-field rule-required rule-ip">\
+                                    <input type="text" id="ip" name="IP" value="~!:IP~!" class="text-field rule-required rule-ip">\
                                     <i class="arrow">&nbsp;</i>\
                             </div>\
                     </div>\
                     <div class="form-row dns-template-box cc">\
-                            <label for="#" class="field-label">Template:</label>\
+                            <label for="selecttemplate" class="field-label">Template:</label>\
                             <span class="select" id="selecttemplate">~!:TPL_DEFAULT_VALUE~! t </span>\
                                 <select name="TPL" class="styled tpl-item">\
                                        ~!:TPL~!\
@@ -149,8 +149,8 @@ App.Templates.html = {
                             <input type="text" value="~!:TTL~!" name="TTL" class="text-field ttl-field rule-required rule-numeric">\
                     </div>\
                     <div class="form-row cc">\
-                            <label for="#" class="field-label">SOA:</label>\
-                            <input type="text" value="~!:SOA~!" name="SOA" class="text-field rule-required rule-ns">\
+                            <label for="soa" class="field-label"><span class="mandatory">SOA:</span></label>\
+                            <input type="text" value="~!:SOA~!" id="soa" name="SOA" class="text-field rule-required rule-ns">\
                     </div -->\
                     <div class="form-row suspended cc">\
 							<label for="#" class="field-label">Suspended:</label>\
@@ -584,8 +584,8 @@ App.Templates.html = {
 									<span class="prop-value">~!:SHELL~!</span>\
 								</span>\
 								<span class="prop-box backups-box">\
-									<span class="prop-title">backups:</span>\
-									<span class="prop-value">retention ~!:BACKUPS~!</span>\
+									<span class="prop-title">backup retention:</span>\
+									<span class="prop-value">~!:BACKUPS~!</span>\
 								</span>\							</div>\
 						</div><!-- // .row-details -->\
 					</div>']

+ 4 - 3
web/test.php

@@ -1,3 +1,4 @@
-<?
-phpinfo();
-?>
+<?php
+echo "<pre>\n";
+exec('sudo /usr/local/vesta/bin/v_list_users json', $out);
+print_r($out);

+ 16 - 16
web/vesta/api/MAIN.class.php

@@ -44,26 +44,26 @@ class MAIN extends AjaxHandler
             return $this->reply(false, null, 'Captcha is invalid ');
         }
         
-        $users = Vesta::execute(Vesta::V_LIST_SYS_USERS, 'json');
-        $email_matched_count = array();
-        
-        if (!preg_match("/^([a-zA-Z0-9])+([a-zA-Z0-9\._-])*@([a-zA-Z0-9_-])+([a-zA-Z0-9\._-]+)+$/",$request->getParameter('email'))) {
-            return $this->reply(false, null, 'Email is invalid');
-        }
-        
-        foreach ($users['data'] as $user) {           
-            if ($user['CONTACT'] == trim($request->getParameter('email'))) {
-                $email_matched_count[] = $user;
+        $cmd = Config::get('sudo_path')." ".Config::get('vesta_functions_path').Vesta::V_LIST_SYS_USERS." 'json'";
+        exec($cmd, $output, $return);
+ 
+        $users = json_decode(implode('', $output), true);
+
+        $login_matched_count = array();
+
+        foreach ($users as $user => $data) {           
+            if ($user == trim($request->getParameter('login'))) {
+                $login_matched_count[$user] = $data;
             }
         }
         
-        if (empty($email_matched_count)) {
+        if (empty($login_matched_count)) {
             return $this->reply(false, null, 'There is no such user.');
         }
 
-        foreach ($email_matched_count as $reset_user) {
+        foreach ($login_matched_count as $reset_user => $data) {
             
-            $secret_key = $reset_user['RKEY'];
+            $secret_key = $data['RKEY'];
             $reset_link = 'https://'.$_SERVER['HTTP_HOST'].'/change_password.php?v='.$secret_key;
             
             $mail_body = <<<MAIL
@@ -73,7 +73,7 @@ class MAIN extends AjaxHandler
                     </a>  
                     <div style="font-family:'Helvetica Neue', Arial, Helvetica, sans-serif;font-size:13px;margin:14px">
                     <h2 style="font-family:'Helvetica Neue', Arial, Helvetica, sans-serif;margin:0 0 16px;font-size:18px;font-weight:normal">
-                        Vesta received a request to reset the password for your account {$reset_user['FNAME']} {$reset_user['LNAME']}?
+                        Vesta received a request to reset the password for your account {$data['FNAME']} {$data['LNAME']}?
                     </h2>
                     <p>
                         If you want to reset your password, click on the link below (or copy and paste the URL into your browser):<br>
@@ -94,9 +94,9 @@ class MAIN extends AjaxHandler
                 </div>
 MAIL;
             
-            $headers           = 'MIME-Version: 1.0' . "\n";
+            $headers            = 'MIME-Version: 1.0' . "\n";
             $headers           .= 'Content-type: text/html; charset=UTF-8' . "\n";
-            $to                 = $request->getParameter('email');
+            $to                 = $data['CONTACT'];
             $subject            = 'Reset your Vesta password';
             $message            = $mail_body;
             mail($to, $subject, $message, $headers);

+ 1 - 1
web/vesta/core/Vesta.class.php

@@ -208,7 +208,7 @@ class Vesta
 	} 
 	else {
             $result['data'] = json_decode(implode('', $output), true);
-        }
+    }
     
         return $result;
     }  

+ 6 - 8
web/vesta/core/VestaSession.class.php

@@ -61,14 +61,12 @@ class VestaSession
 
     public function getUserRole()
     {   
-      //        if (isset($_SESSION['user'])) {
-            if($_SESSION['user'] == 'vesta'){
-                return Vesta::ADMIN;
-            }
-            else{
-                return Vesta::USER;
-            }
-            //        }
+        if($_SESSION['user'] == 'vesta'){
+            return Vesta::ADMIN;
+        }
+        else{
+            return Vesta::USER;
+        }
 
         print json_encode(array('result' => "NOT_AUTHORISED"));
         exit;