55 |
--------------------------------------------------------------------------------
/design/admin/templates/userpaex/password.tpl:
--------------------------------------------------------------------------------
1 | {* DO NOT EDIT THIS FILE! Use an override template instead. *}
2 |
3 |
4 | {* DESIGN: Header START *}
5 |
{"Change password for user"|i18n("mbpaex/userpaex")}
28 |
29 | {* If we are editing a user, show password status, if not and the current user
30 | have permissions, show a checkbox to choose update children *}
31 | {if $attribute.content.is_user}
32 |
33 |
34 |
41 |
42 |
43 |
44 | {elseif $attribute.content.can_edit}
45 |
46 |
47 |
48 |
49 |
50 |
51 |
52 | {/if}
53 |
--------------------------------------------------------------------------------
/cronjobs/ezmbpaex_updatechildren.php:
--------------------------------------------------------------------------------
1 | variable( 'mbpaexSettings','UpdateChildrenUser' );
13 | // Default to admin if user is not found in the ini
14 | if ( !trim( $updateChildrenUser ) )
15 | $updateChildrenUser = 'admin';
16 |
17 | $user = eZUser::fetchByName( $updateChildrenUser );
18 | eZUser::setCurrentlyLoggedInUser( $user, $user->attribute( 'contentobject_id' ) );
19 |
20 | if ( $user->isLoggedIn() )
21 | {
22 | $cli->output( "eZPaEx: Update children process start" );
23 |
24 | ini_set( 'max_execution_time', 0 );
25 | ini_set( 'memory_limit', '-1' );
26 |
27 | eZDebug::addTimingPoint( 'Fetch update pending list' );
28 | // Get list of paex objects marked to updatechildren
29 | $pendingList = eZPaEx::fetchUpdateChildrenPendingList();
30 | $pendingListCount = count( $pendingList );
31 |
32 | if ( !$pendingListCount )
33 | {
34 | $cli->output( "No pending update subtrees found" );
35 | }
36 | else
37 | {
38 | $cli->output( "Found " . $pendingListCount . " ezpaex objects with pending updatechildren" );
39 | $pendingIdList = array();
40 | foreach ($pendingList as $pendingObject)
41 | {
42 | $pendingIdList[] = $pendingObject->attribute( 'contentobject_id' );
43 | }
44 |
45 | // Fetch array of nodes corresponding to objects in the pendingIDList to sort them by depth
46 | $nodeArray = eZContentObjectTreeNode::findMainNodeArray( $pendingIdList, false );
47 |
48 | // Make an array of objects ids with its deph based on the corresponding node
49 | $objectDepthList = array();
50 | foreach ($nodeArray as $key => $node)
51 | {
52 | $objectDepthList[0][$key] = $node["depth"];
53 | $objectDepthList[1][$key] = $node["contentobject_id"];
54 | }
55 | // Sort objectDepthList by depth to apply updatechildren in the right order
56 | if ( !array_multisort( $objectDepthList[0], SORT_ASC, $objectDepthList[1], SORT_ASC ) )
57 | {
58 | eZDebug::writeError( 'Error in array_multisort', 'ezmbpaex_updatechildren.php' );
59 | }
60 | else
61 | {
62 | // Generate array of paex objects to update
63 | $paexObjectArray = array();
64 | foreach ( $objectDepthList[1] as $contentobjectId )
65 | {
66 | if ( isset( $pendingList[$contentobjectId] ) )
67 | {
68 | // Generate update children data for every pending object in pendingIDList
69 | $paexObjectArray = $pendingList[$contentobjectId]->generateUpdateChildren( $paexObjectArray );
70 | }
71 | else
72 | {
73 | eZDebug::writeError( 'Found contentobject_id [' . $contentobjectId . '] not present in the pendingIDList', 'ezmbpaex_updatechildren.php' );
74 | }
75 | }
76 |
77 | // Reset pending object updatechildren attribute in pendingIDList objects and add to the array of paex objects to update
78 | foreach ( $pendingList as $pendingObject )
79 | {
80 | $pendingObject->setAttribute( 'updatechildren', 0 );
81 | $paexObjectArray[$pendingObject->attribute( 'contentobject_id' )] = $pendingObject;
82 | }
83 |
84 | // Store updated paex objects in the DB
85 | $db = eZDB::instance();
86 | $db->begin();
87 |
88 | foreach ( $paexObjectArray as $paexObject )
89 | {
90 | $paexObject->store();
91 | eZContentCacheManager::clearContentCacheIfNeeded( $paexObject->attribute( 'contentobject_id' ) );
92 | }
93 | $db->commit();
94 | }
95 | }
96 |
97 | $cli->output( "eZPaEx: Update children process end" );
98 | }
99 |
100 | ?>
--------------------------------------------------------------------------------
/login_handler/ezpaexuser.php:
--------------------------------------------------------------------------------
1 | attribute( 'contentobject_id' );
60 | $paex = eZPaEx::getPaEx( $userID, true );
61 |
62 | if ( $paex instanceof eZPaEx && $paex->isExpired() )
63 | {
64 | self::passwordHasExpired( $user );
65 | return false;
66 | }
67 | else
68 | {
69 | self::loginSucceeded( $user );
70 | return $user;
71 | }
72 | }
73 | else
74 | {
75 | self::loginFailed( $user, $login );
76 | return false;
77 | }
78 |
79 | return $user;
80 | }
81 |
82 | /**
83 | * Writes audit information and redirects the user to the password change form.
84 | *
85 | * @param eZUser $user
86 | */
87 | protected static function passwordHasExpired( $user )
88 | {
89 | $userID = $user->attribute( 'contentobject_id' );
90 |
91 | // Password expired
92 | eZDebugSetting::writeDebug( 'kernel-user', $user, 'user password expired' );
93 |
94 | // Failed login attempts should be logged
95 | $userIDAudit = isset( $userID ) ? $userID : 'null';
96 | $loginEscaped = eZDB::instance()->escapeString( $user->attribute( 'login' ) );
97 | eZAudit::writeAudit( 'user-failed-login', array( 'User id' => $userIDAudit,
98 | 'User login' => $loginEscaped,
99 | 'Comment' => 'Failed login attempt: Password Expired. eZPaExUser::loginUser()' ) );
100 |
101 | // Redirect user to password change form
102 | self::redirectToChangePasswordForm( $userID );
103 | }
104 |
105 | /**
106 | * Performs a redirect to the password change form
107 | *
108 | * @param int $userID
109 | */
110 | protected static function redirectToChangePasswordForm( $userID )
111 | {
112 | $http = eZHTTPTool::instance();
113 | $url = self::$changePasswordFormURL . $userID;
114 | eZURI::transformURI( $url );
115 | $http->redirect( $url );
116 | }
117 | }
118 |
119 | ?>
120 |
--------------------------------------------------------------------------------
/design/standard/templates/userpaex/forgotpassword.tpl:
--------------------------------------------------------------------------------
1 | {* DO NOT EDIT THIS FILE! Use an override template instead. *}
2 |
3 |
4 |
5 |
6 | {if $link}
7 |
8 | {"A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password."|i18n('mbpaex/userpaex/forgotpassword',,array($email))}
9 |
10 | {else}
11 | {if $wrong_email}
12 |
13 |
{"There is no registered user with that email address."|i18n('mbpaex/userpaex/forgotpassword')}
140 |
--------------------------------------------------------------------------------
/modules/userpaex/password.php:
--------------------------------------------------------------------------------
1 | attribute( "contentobject_id" );
13 | $http = eZHTTPTool::instance();
14 | $Module = $Params["Module"];
15 | $message = 0;
16 | $oldPasswordNotValid = 0;
17 | $newPasswordNotMatch = 0;
18 | $newPasswordTooShort = 0;
19 | $newPasswordNotValidate = 0;
20 | $newPasswordMustDiffer = 0;
21 | $userRedirectURI = '';
22 |
23 | $userRedirectURI = $Module->actionParameter( 'UserRedirectURI' );
24 |
25 | if ( $http->hasSessionVariable( "LastAccessesURI" ) )
26 | $userRedirectURI = $http->sessionVariable( "LastAccessesURI" );
27 |
28 | $redirectionURI = $userRedirectURI;
29 | if ( $redirectionURI == '' )
30 | $redirectionURI = $ini->variable( 'SiteSettings', 'DefaultPage' );
31 |
32 | if( !isset( $oldPassword ) )
33 | $oldPassword = '';
34 |
35 | if( !isset( $newPassword ) )
36 | $newPassword = '';
37 |
38 | if( !isset( $confirmPassword ) )
39 | $confirmPassword = '';
40 |
41 | if ( is_numeric( $Params["UserID"] ) )
42 | $UserID = $Params["UserID"];
43 | else
44 | $UserID = false;
45 |
46 | $user = eZUser::fetch( $UserID );
47 |
48 | if ( $http->hasPostVariable( "OKButton" ) && $user)
49 | {
50 | if ( $http->hasPostVariable( "oldPassword" ) )
51 | {
52 | $oldPassword = $http->postVariable( "oldPassword" );
53 | }
54 | if ( $http->hasPostVariable( "newPassword" ) )
55 | {
56 | $newPassword = $http->postVariable( "newPassword" );
57 | }
58 | if ( $http->hasPostVariable( "confirmPassword" ) )
59 | {
60 | $confirmPassword = $http->postVariable( "confirmPassword" );
61 | }
62 |
63 | $login = $user->attribute( "login" );
64 | $type = $user->attribute( "password_hash_type" );
65 | $hash = $user->attribute( "password_hash" );
66 | $site = $user->site();
67 |
68 | if ( $user->authenticateHash( $login, $oldPassword, $site, $type, $hash ) ) // Old password is correct
69 | {
70 | if ( $newPassword == $confirmPassword )
71 | {
72 | if ( !$user->validatePassword($newPassword) )
73 | {
74 | // if audit is enabled password changes should be logged
75 | eZAudit::writeAudit( 'user-password-change-self-fail', array( 'UserID: ' => $UserID, 'Login: ' => $login,
76 | 'Comment: ' => 'Password not pass standard validation' ) );
77 |
78 | $newPasswordNotValidate = 1;
79 | }
80 | else
81 | {
82 | // Patch for use mbpaex::validatePassword
83 | $paex = eZPaEx::getPaEx( $UserID );
84 | if (!$paex->validatePassword($newPassword))
85 | {
86 | // if audit is enabled password changes should be logged
87 | eZAudit::writeAudit( 'user-password-change-self-fail', array( 'UserID: ' => $UserID, 'Login: ' => $login,
88 | 'Comment: ' => 'Password not pass PAEX validation' ) );
89 | $newPasswordNotValidate = 1;
90 | }
91 | else
92 | {
93 | $oldHash = $user->createHash( $login, $oldPassword, $site, $type );
94 | $newHash = $user->createHash( $login, $newPassword, $site, $type );
95 | if ($oldHash == $newHash)
96 | {
97 | // if audit is enabled password changes should be logged
98 | eZAudit::writeAudit( 'user-password-change-self-fail', array( 'UserID: ' => $UserID, 'Login: ' => $login,
99 | 'Comment: ' => 'New and old password are the same' ) );
100 | $newPasswordMustDiffer = 1;
101 | }
102 | else
103 | {
104 | // if audit is enabled password changes should be logged
105 | eZAudit::writeAudit( 'user-password-change-self', array( 'UserID: ' => $UserID, 'Login: ' => $login ) );
106 |
107 | $user->setAttribute( "password_hash", $newHash );
108 | $user->store();
109 | $paex->resetPasswordLastUpdated();
110 | $oldPassword = '';
111 |
112 | eZUser::setCurrentlyLoggedInUser( $user, $UserID );
113 | eZUser::updateLastVisit( $UserID, true );
114 |
115 | if ( $http->hasPostVariable( "RedirectOnChange" ) )
116 | {
117 | return $Module->redirectTo( $http->postVariable( "RedirectOnChange" ) );
118 | }
119 | eZRedirectManager::redirectTo( $Module, $redirectionURI );
120 | return;
121 | }
122 | }
123 | }
124 | $newPassword = '';
125 | $confirmPassword = '';
126 | $message = true;
127 | }
128 | else
129 | {
130 | // if audit is enabled password changes should be logged
131 | eZAudit::writeAudit( 'user-password-change-self-fail', array( 'UserID: ' => $UserID, 'Login: ' => $login,
132 | 'Comment: ' => 'Password not match password confirmation' ) );
133 | $newPassword = "";
134 | $confirmPassword = "";
135 | $newPasswordNotMatch = 1;
136 | $message = true;
137 | }
138 | }
139 | else
140 | {
141 | // if audit is enabled password changes should be logged
142 | eZAudit::writeAudit( 'user-password-change-self-fail', array( 'UserID: ' => $UserID, 'Login: ' => $login,
143 | 'Comment: ' => 'Old password incorrect' ) );
144 | $oldPassword = "";
145 | $oldPasswordNotValid = 1;
146 | $message = true;
147 | }
148 | }
149 |
150 | if ( $http->hasPostVariable( "CancelButton" ) || !$user )
151 | {
152 | if ( $http->hasPostVariable( "RedirectOnCancel" ) )
153 | {
154 | return $Module->redirectTo( $http->postVariable( "RedirectOnCancel" ) );
155 | }
156 | eZRedirectManager::redirectTo( $Module, $redirectionURI );
157 | return;
158 | }
159 |
160 | $Module->setTitle( "Edit user information" );
161 | // Template handling
162 | $tpl = eZTemplate::factory();
163 | $tpl->setVariable( "module", $Module );
164 | $tpl->setVariable( "http", $http );
165 | $tpl->setVariable( "userID", $UserID );
166 | $tpl->setVariable( "userAccount", $user );
167 | $tpl->setVariable( "oldPassword", $oldPassword );
168 | $tpl->setVariable( "newPassword", $newPassword );
169 | $tpl->setVariable( "confirmPassword", $confirmPassword );
170 | $tpl->setVariable( "oldPasswordNotValid", $oldPasswordNotValid );
171 | $tpl->setVariable( "newPasswordNotMatch", $newPasswordNotMatch );
172 | $tpl->setVariable( "newPasswordTooShort", $newPasswordTooShort );
173 | $tpl->setVariable( "newPasswordNotValidate", $newPasswordNotValidate );
174 | $tpl->setVariable( "newPasswordMustDiffer", $newPasswordMustDiffer );
175 | $tpl->setVariable( "message", $message );
176 |
177 | $Result = array();
178 | $Result['path'] = array( array( 'text' => ezpI18n::tr( 'kernel/user', 'User' ),
179 | 'url' => false ),
180 | array( 'text' => ezpI18n::tr( 'kernel/user', 'Change password' ),
181 | 'url' => false ) );
182 | $Result['content'] = $tpl->fetch( "design:userpaex/password.tpl" );
183 |
184 | $currentuser = eZUser::currentUser();
185 | if ( !$currentuser->isLoggedIn() )
186 | {
187 | if ( $ini->variable( 'SiteSettings', 'LoginPage' ) == 'custom' )
188 | {
189 | $Result['pagelayout'] = 'loginpagelayout.tpl';
190 | }
191 | }
192 | ?>
193 |
--------------------------------------------------------------------------------
/doc/INSTALL.txt:
--------------------------------------------------------------------------------
1 | Password Expiration Extension (v1.0RC1)
2 | ================================================
3 |
4 | 0) Release Info
5 | 1) Install
6 | 2) Brief usage instructions
7 | 3) Forgot password procedure
8 | 4) UpdateChildren feature
9 | 5) "Password about to Expire" notification
10 | 6) Audit logs
11 | 7) Hook for mbtoken usage
12 | 8) TODO list
13 | 9) RFE
14 | 10) About
15 |
16 | 0. Release Info
17 | ------------
18 |
19 | Current version: mbPaEx_1.4
20 | Release Date: March 29th 2011.
21 |
22 | Compatible with eZ Publish v4.x
23 |
24 |
25 | 1. Install
26 | -------
27 |
28 | - Put the ezmbpaex folder inside your extension folder
29 |
30 | - Update the ezpublish database, execute from , replacing
31 | with the database system you're running eZ Publish on (mysql, oracle or postgresql):
32 |
33 | $ mysql -u -p < extension/ezmbpaex/sql//mbpaex.sql
34 |
35 | - Customize default settings in
36 | extension/ezmbpaex/settings/mbpaex.ini (or an override):
37 |
38 | [mbpaexSettings]
39 | # Regular expression used for password validation when
40 | # none is defined in the contentobject
41 | PasswordValidationRegexp=
42 |
43 | # Default lifetime for password in DAYS
44 | # 0 means no limit (passwords never expire)
45 | DefaultPasswordLifeTime=0
46 |
47 | # Number of seconds before password expiration to send a
48 | # mail notification to the user
49 | # Default 172800 (2 days)
50 | ExpirationNotification=172800
51 |
52 | # Number of seconds that the forgot password generated hash will be valid
53 | # Default 86400 (1 day)
54 | ForgotPasswordHashLifeTime=86400
55 |
56 | # Login of the eZ user used in the ezmbpaex_updatechildren cronjob, must
57 | # have access to read the Users section.
58 | UpdateChildrenUser=admin
59 |
60 | - Activate the extension in your site.ini
61 |
62 | ActiveExtensions[]=ezmbpaex
63 |
64 | - To prevent undesired access to default user module views that don't take care about the
65 | password expiration settings there should only be enabled the views needed, then standard
66 | ones will get access denied. These changes should be added to the global override of
67 | site.ini:
68 |
69 | [SiteAccessSettings]
70 | AnonymousAccessList[]
71 | AnonymousAccessList[]=user/success
72 | AnonymousAccessList[]=user/activate
73 | AnonymousAccessList[]=userpaex/password
74 | AnonymousAccessList[]=userpaex/forgotpassword
75 |
76 | [RoleSettings]
77 | PolicyOmitList[]
78 | PolicyOmitList[]=user/login
79 | PolicyOmitList[]=user/logout
80 | PolicyOmitList[]=userpaex/password
81 | PolicyOmitList[]=userpaex/forgotpassword
82 |
83 | - Setup override template used in replacement of node/view/full.tpl to display
84 | users and users groups in admin interface:
85 |
86 | Inside /extension/ezmbpaex/settings/siteaccess you will find a folder
87 | that will be used in the "admin" siteaccess. If your admin siteaccess has a
88 | different name, the content of the override.ini.append.php file must be added
89 | to the override.ini of your custom admin siteaccess.
90 |
91 | - Re-generate autoloads array to include new classes present in mbPaEx extension:
92 |
93 | $ bin/php/ezpgenerateautoloads.php --extension
94 |
95 | - Clear all caches
96 |
97 | - After installation, a new datatype would be available to add as an attribute in
98 | the User and User Group classes, "Password Expiration". You must add this datatype
99 | to all your User group and User content classes if you want to use the extension.
100 |
101 |
102 | 2. Brief usage instructions
103 | ------------------------
104 |
105 | When the attribute gets created it takes the values set in the ini file as default
106 | values.
107 |
108 | To prevent that all existing users are forced to change their passwords, there is
109 | a script available to reset the password_last_updated value of all users to current
110 | time. You can run this script with the following command:
111 |
112 | $ php extension/ezmbpaex/install/scripts/setpasswordlastupdated.php
113 |
114 | When you customize the values in a user group, a checkbox would appear to update
115 | children nodes with the values of the current group, this way you can customize
116 | the password lifetime and validation regexp per group easily. (See point 4)
117 |
118 | There is a new function to restrict if a user can edit the paex data, editpaex.
119 | If anyone other than admin should be able to update the paex data, a new policy
120 | with this function should be added to his role.
121 |
122 | When someone changes the password for another user, the password last update time
123 | is set to 0 to force the user change his password the next time he tries to log in.
124 |
125 | NOTE: There must be a password lifetime defined in order to force the user
126 | change his password. If PasswordLifeTime is set to 0 the user never gets
127 | forced to change its password (the password never expires).
128 |
129 | When the password for a user is expired, the user never gets logged in, he only
130 | can access the change password view from userpaex module to change his password.
131 |
132 | When a user changes their password, the system prevents to enter the same
133 | password currently set, this way a new different one must be used.
134 |
135 | When a user or group is published the first time, if the current user don't have
136 | "editpaex" permission set in their roles, the system automatically obtains the
137 | actual paex data set in parent.
138 | If the user have "editpaex" permission, the values entered in the form will be used,
139 | to use values set in parent, these fields must be cleared.
140 |
141 |
142 | 3. Forgot password procedure
143 | -------------------------
144 |
145 | There is a new view in the userpaex module, forgotpassword, to manage the forgot
146 | password function.
147 |
148 | Has small modifications from the eZ one, to note:
149 |
150 | - The user is required to enter his email address
151 | - A new hash key is generated, and the user receives an email with a link pointing
152 | to a form to choose a new password. Also in this email, there is an expiration
153 | datetime to inform the user that this link should be removed.
154 | - When the user clicks the link and sets a new password, the hash key is removed
155 | from the forgot password table.
156 | - The time the hash key remains valid is defined in the ini value
157 | ForgotPasswordHashLifeTime in seconds, with a default value of 86400 (24 hours)
158 | - If a second hash key is requested without having used the previous one, they
159 | will be removed, so only the last key generated is valid.
160 |
161 |
162 | 4. UpdateChildren feature
163 | ----------------------
164 |
165 | In order to prevent failures during the process and to make the user edit process
166 | quicker, the update children has moved to a cronjob, so a new cronjob task has to
167 | be set for the update be actually done.
168 | The cronjob part defined to do the actual update of the children is
169 | "ezmbpaex_updatechildren"
170 |
171 | The cronjob can be manually run with the following command from folder:
172 |
173 | $php runcronjobs.php ezmbpaex_updatechildren
174 |
175 | When a node is marked to update his children, a notification text will be shown
176 | in the admin view template for that node.
177 |
178 | Only group nodes have the updatechildren checkbox displayed in the edit template.
179 |
180 | The updates are applied from outer to inner nodes, so, if you have a node set to
181 | update his chidren, and then one of the children nodes also set to update his ones,
182 | that children node will not be updated with the data from parent, instead, their
183 | children will be updated with his data.
184 |
185 | It's ok to set up the cronjob to be run in the frequent cronjob part.
186 |
187 |
188 | 5. "Password about to Expire" notification
189 | ---------------------------------------
190 |
191 | Optionally if you want your users get notified when their password is about to
192 | expire, a new cronjob can be set up to search users based on their password last
193 | updated time and password lifetime, and if it results in a password remain time
194 | less that configured expiration notification time, a mail will be generated and
195 | sent to the users so they can change their password prior to expiration.
196 |
197 | The cronjob can be manually run with the following command from folder:
198 |
199 | $ php runcronjobs.php ezmbpaex_send_expiry_notifications
200 |
201 | Only one notification sent to each user, and no more notifications are sent until
202 | the user changes his password and it expires again.
203 |
204 |
205 | 6. Audit logs
206 | ----------
207 |
208 | In order to enhance security new audit functions have been defined for ezmbpaex operations
209 | that can be enabled in an override for the audit.ini settings file:
210 |
211 | - user-password-change
212 |
213 | Logs pasword changes made to third party accounts (admin changing password for a
214 | user)
215 |
216 | - user-password-change-self
217 |
218 | Logs when users change their own password
219 |
220 | - user-password-change-self-fail
221 |
222 | Logs when users try to change their own password and send wrong current password
223 |
224 | - user-forgotpassword
225 |
226 | User has made use of the forgotpassword function of userpaex module
227 |
228 | - user-forgotpassword-fail
229 |
230 | User tries to made use of the forgotpassword function of userpaex module but
231 | some error occurred (the actual error is also logged)
232 |
233 | 7. Hook for mbtoken usage
234 | ----------------------
235 |
236 | The loginhandler has been updated to include the possibility to use the mbtoken extension,
237 | that will add extra security to the login process by the use of a security token.
238 | More info available in mbtoken extension.
239 |
240 |
241 | 8. TODO list
242 | ---------
243 |
244 | - Prevent user enter same password that have set, when editting user contentobject
245 | from admin interface (I think that password history has to be implemented to do
246 | this).
247 |
248 |
249 | 9. Request for enhancement
250 | ------------------------
251 |
252 | - Password history
253 |
254 |
255 | 10. About ezmbpaex
256 | --------------
257 |
258 | This extension was developed by Microblau with eZ Systems support.
259 |
--------------------------------------------------------------------------------
/modules/userpaex/forgotpassword.php:
--------------------------------------------------------------------------------
1 | setVariable( 'generated', false );
12 | $tpl->setVariable( 'wrong_email', false );
13 | $tpl->setVariable( 'link', false );
14 | $tpl->setVariable( 'wrong_key', false );
15 | $tpl->setVariable( 'password_form', false );
16 | $tpl->setVariable( 'newPasswordNotValidate', false );
17 | $tpl->setVariable( 'newPasswordMustDiffer', false );
18 | $tpl->setVariable( 'password_changed', false );
19 | $tpl->setVariable( 'newPasswordNotMatch', false );
20 |
21 | $http = eZHTTPTool::instance();
22 | $module = $Params["Module"];
23 | $hashKey = $Params["HashKey"];
24 | $hashKeyValidated = false;
25 | $mbpaex_ini = eZINI::instance('mbpaex.ini');
26 | $forgotPasswdHashLifeTime = $mbpaex_ini->variable( "mbpaexSettings", "ForgotPasswordHashLifeTime" );
27 | $ini = eZINI::instance();
28 |
29 | if ( strlen( $hashKey ) == 32 )
30 | {
31 | $currentTime = time();
32 |
33 | $forgotPasswdObj = eZForgotPassword::fetchByKey( $hashKey );
34 | if (!is_object($forgotPasswdObj)) // HashKey not found
35 | {
36 | // if audit is enabled password changes should be logged
37 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'HashKey' => $hashKey,
38 | 'Comment' => 'HashKey not found' ) );
39 |
40 | $tpl->setVariable( 'wrong_key', true );
41 | }
42 | elseif (($currentTime - $forgotPasswdObj->attribute('time')) > $forgotPasswdHashLifeTime) // HashKey expired
43 | {
44 | // if audit is enabled password changes should be logged
45 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'HashKey' => $hashKey,
46 | 'Comment' => 'HashKey expired, proceed to remove' ) );
47 |
48 | $forgotPasswdObj->remove(); // Remove expired hash
49 | $tpl->setVariable( 'wrong_key', true );
50 | }
51 | else // HashKey OK -> show/process change password form
52 | {
53 | $tpl->setVariable( 'password_form', true );
54 | $tpl->setVariable( 'HashKey', $hashKey );
55 | $hashKeyValidated = true;
56 | }
57 | }
58 | else if ( strlen( $hashKey ) > 4 )
59 | {
60 | // if audit is enabled password changes should be logged
61 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'HashKey' => $hashKey,
62 | 'Comment' => 'HashKey not found' ) );
63 |
64 | $tpl->setVariable( 'wrong_key', true );
65 | }
66 |
67 | if ( $module->isCurrentAction( "Generate" ) )
68 | {
69 | $passwordLength = $ini->variable( "UserSettings", "GeneratePasswordLength" );
70 | $password = eZUser::createPassword( $passwordLength );
71 | $passwordConfirm = $password;
72 |
73 | if ( $module->hasActionParameter( "Email" ) && eZMail::validate($module->actionParameter( "Email" )) )
74 | {
75 | $email = $module->actionParameter( "Email" );
76 | if ( trim( $email ) != "" )
77 | {
78 | $users = eZPersistentObject::fetchObjectList( eZUser::definition(),
79 | null,
80 | array( 'email' => $email ),
81 | null,
82 | null,
83 | true );
84 | }
85 | if ( !empty( $users ) )
86 | {
87 | $user = $users[0];
88 | $time = time();
89 | $hashKey = md5( $time . ":" . mt_rand() );
90 |
91 | $db = eZDB::instance();
92 | $db->begin();
93 |
94 | // Remove previous generated hash keys for same user
95 | eZForgotPassword::removeByUserID($user->id());
96 |
97 | $forgotPasswdObj = eZForgotPassword::createNew( $user->id(), $hashKey, $time );
98 | $forgotPasswdObj->store();
99 |
100 | $userToSendEmail = $user;
101 | $receiver = $email;
102 |
103 | $mail = new eZMail();
104 | if ( !$mail->validate( $receiver ) )
105 | {
106 | }
107 | $tpl = eZTemplate::factory();
108 | $tpl->setVariable( 'user', $userToSendEmail );
109 | $tpl->setVariable( 'object', $userToSendEmail->attribute( 'contentobject' ) );
110 | $tpl->setVariable( 'password', $password );
111 | $tpl->setVariable( 'link', true );
112 | $tpl->setVariable( 'hash_key', $hashKey );
113 | $tpl->setVariable( 'hash_key_lifetime', date("d/m/Y H:i",time() + $forgotPasswdHashLifeTime));
114 |
115 | $http = eZHTTPTool::instance();
116 | $http->UseFullUrl = true;
117 | $templateResult = $tpl->fetch( 'design:userpaex/forgotpasswordmail.tpl' );
118 | $http->UseFullUrl = false;
119 | $emailSender = $ini->variable( 'MailSettings', 'EmailSender' );
120 | if ( !$emailSender )
121 | $emailSender = $ini->variable( 'MailSettings', 'AdminEmail' );
122 | $mail->setSender( $emailSender );
123 | $mail->setReceiver( $receiver );
124 | $subject = ezpI18n::tr( 'kernel/user/register', 'Registration info' );
125 | if ( $tpl->hasVariable( 'subject' ) )
126 | $subject = $tpl->variable( 'subject' );
127 | $mail->setSubject( $subject );
128 | $mail->setBody( $templateResult );
129 | $mailResult = eZMailTransport::send( $mail );
130 | $tpl->setVariable( 'email', $email );
131 | $db->commit();
132 |
133 | // if audit is enabled password changes should be logged
134 | eZAudit::writeAudit( 'user-forgotpassword', array( 'Email' => $email,
135 | 'Comment' => 'Forgotpassword email sent' ) );
136 |
137 | }
138 | else
139 | {
140 | // if audit is enabled password changes should be logged
141 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'Email' => $email,
142 | 'Comment' => 'Email address not found' ) );
143 |
144 | $tpl->setVariable( 'wrong_email', $email );
145 | }
146 | }
147 | }
148 | else if ( $module->isCurrentAction( "ChangePassword" ) && $hashKeyValidated )
149 | {
150 | if ( $module->hasActionParameter( "NewPassword" ) )
151 | $newPassword = $module->actionParameter( "NewPassword" );
152 | else
153 | $newPassword = false;
154 |
155 | if ( $module->hasActionParameter( "NewPasswordConfirm" ) )
156 | $confirmPassword = $module->actionParameter( "NewPasswordConfirm" );
157 | else
158 | $confirmPassword = false;
159 |
160 | // The forgotPasswdObj was previously validated, fetch the corresponding user object
161 | $UserID = $forgotPasswdObj->attribute( 'user_id' );
162 | $user = eZUser::fetch($UserID);
163 | $login = $user->attribute( "login" );
164 | $type = $user->attribute( "password_hash_type" );
165 | $hash = $user->attribute( "password_hash" );
166 | $site = $user->site();
167 |
168 | if ( $newPassword == $confirmPassword )
169 | {
170 | if ( !$user->validatePassword($newPassword) ) // Password must meet "old" validation rules
171 | {
172 | // if audit is enabled password changes should be logged
173 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'UserID' => $UserID, 'Login' => $login,
174 | 'Comment: ' => 'Password not pass standard validation' ) );
175 |
176 | $tpl->setVariable( 'newPasswordNotValidate', true);
177 | }
178 | else
179 | {
180 | // Patch for use mbpaex::validatePassword
181 | $paex = eZPaEx::getPaEx($UserID);
182 | if (!$paex->validatePassword($newPassword))
183 | {
184 | // if audit is enabled password changes should be logged
185 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'UserID' => $UserID, 'Login' => $login,
186 | 'Comment: ' => 'Password not pass PAEX validation' ) );
187 |
188 | $tpl->setVariable( 'newPasswordNotValidate', true);
189 | }
190 | else
191 | {
192 | $newHash = $user->createHash( $login, $newPassword, $site, $type );
193 | if ($newHash == $user->attribute('password_hash'))
194 | {
195 | // if audit is enabled password changes should be logged
196 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'UserID' => $UserID, 'Login' => $login,
197 | 'Comment: ' => 'New and old password are the same' ) );
198 |
199 | $tpl->setVariable( 'newPasswordMustDiffer', true);
200 | }
201 | else
202 | {
203 | // if audit is enabled password changes should be logged
204 | eZAudit::writeAudit( 'user-forgotpassword', array( 'UserID' => $UserID, 'Login' => $login,
205 | 'Comment: ' => 'Password changed successfully' ) );
206 |
207 | $user->setAttribute( "password_hash", $newHash );
208 | $user->store();
209 | $paex->resetPasswordLastUpdated();
210 |
211 | $forgotPasswdObj->remove();
212 | $tpl->setVariable( 'password_changed', true);
213 | }
214 | }
215 | }
216 | }
217 | else
218 | {
219 | // if audit is enabled password changes should be logged
220 | eZAudit::writeAudit( 'user-forgotpassword-fail', array( 'UserID' => $UserID, 'Login' => $login,
221 | 'Comment: ' => 'Password not match password confirmation' ) );
222 |
223 | $tpl->setVariable( 'newPasswordNotMatch', true);
224 | }
225 | }
226 |
227 | $Result = array();
228 | $Result['content'] = $tpl->fetch( 'design:userpaex/forgotpassword.tpl' );
229 | $Result['path'] = array( array( 'text' => ezpI18n::tr( 'kernel/user', 'User' ),
230 | 'url' => false ),
231 | array( 'text' => ezpI18n::tr( 'kernel/user', 'Forgot password' ),
232 | 'url' => false ) );
233 |
234 | if ( $ini->variable( 'SiteSettings', 'LoginPage' ) == 'custom' )
235 | {
236 | $Result['pagelayout'] = 'loginpagelayout.tpl';
237 | }
238 |
239 | ?>
240 |
--------------------------------------------------------------------------------
/translations/untranslated/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 |
9 |
10 |
11 | Manage versions
12 |
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 |
20 |
21 |
22 | Node ID
23 |
24 |
25 |
26 | Object ID
27 |
28 |
29 |
30 | Another language
31 |
32 |
33 |
34 | Edit
35 |
36 |
37 |
38 | Edit the contents of this item.
39 |
40 |
41 |
42 | Not available
43 |
44 |
45 |
46 | You do not have permission to edit this item.
47 |
48 |
49 |
50 | Move
51 |
52 |
53 |
54 | Move this item to another location.
55 |
56 |
57 |
58 | You do not have permission to move this item to another location.
59 |
60 |
61 |
62 | Remove
63 |
64 |
65 |
66 | Remove this item.
67 |
68 |
69 |
70 | You do not have permission to remove this item.
71 |
72 |
73 |
74 | Preview
75 |
76 |
77 |
78 | New translation
79 |
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 |
87 |
88 |
89 | Change name, email, password, etc.
90 |
91 |
92 |
93 | Change information
94 |
95 |
96 |
97 | Change user info
98 |
99 |
100 |
101 | Change password for <%username>.
102 |
103 |
104 |
105 | Change password
106 |
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 |
111 |
112 |
113 | Shopping basket (%basket_count)
114 |
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 |
119 |
120 |
121 | Logout from the system.
122 |
123 |
124 |
125 | Logout
126 |
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Your account information
133 |
134 |
135 |
136 | Email
137 |
138 |
139 |
140 |
141 | kernel/user
142 |
143 | User
144 |
145 |
146 |
147 | Forgot password
148 |
149 |
150 |
151 | Change password
152 |
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 |
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 |
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 |
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 |
176 |
177 |
178 | The password doesn't match the validation rule.
179 |
180 |
181 |
182 | Wrong value in updatechildren field
183 |
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 |
191 |
192 |
193 | Password LifeTime (DAYS)
194 |
195 |
196 |
197 | Expiration Notification (SECONDS)
198 |
199 |
200 |
201 | Current password status:
202 |
203 |
204 |
205 | expired
206 |
207 |
208 |
209 | active
210 |
211 |
212 |
213 | Update children nodes?
214 |
215 |
216 |
217 | undefined
218 |
219 |
220 |
221 | Password status
222 |
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 |
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 |
234 |
235 |
236 | Please retype your old password.
237 |
238 |
239 |
240 | Password didn't match, please retype your new password.
241 |
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 |
246 |
247 |
248 | New password must be different from the old one. Please choose another password.
249 |
250 |
251 |
252 | Password successfully updated.
253 |
254 |
255 |
256 | Old password
257 |
258 |
259 |
260 | New password
261 |
262 |
263 |
264 | Retype password
265 |
266 |
267 |
268 | OK
269 |
270 |
271 |
272 | Cancel
273 |
274 |
275 |
276 | %siteurl your password is about to expire
277 |
278 |
279 |
280 | Your password is about to expire
281 |
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | Click here to set your new password
288 |
289 |
290 |
291 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
292 |
293 |
294 |
295 | There is no registered user with that email address.
296 |
297 |
298 |
299 | The password has been changed successfully.
300 |
301 |
302 |
303 | The passwords do not match. Please, be sure to enter the same password in both fields.
304 |
305 |
306 |
307 | The new password is invalid, please choose new one.
308 |
309 |
310 |
311 | Choose a new password
312 |
313 |
314 |
315 | Enter your desired new password in the form below.
316 |
317 |
318 |
319 | Password
320 |
321 |
322 |
323 | Password Confirm
324 |
325 |
326 |
327 | Change password
328 |
329 |
330 |
331 | The key is invalid or has been used.
332 |
333 |
334 |
335 | Have you forgotten your password?
336 |
337 |
338 |
339 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
340 |
341 |
342 |
343 | Email
344 |
345 |
346 |
347 | Generate new password
348 |
349 |
350 |
351 | %siteurl forgot password
352 |
353 |
354 |
355 | This link is valid until %1, after that time you should generate a new one.
356 |
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/por-BR/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 | Ver e gerenciar (copiar, deletar, etc.) as versões deste objeto.
9 |
10 |
11 | Manage versions
12 | Gerenciar versões
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 | Última modificação
20 |
21 |
22 | Node ID
23 | ID do nó
24 |
25 |
26 | Object ID
27 | ID do objeto
28 |
29 |
30 | Another language
31 | Outro idioma
32 |
33 |
34 | Edit
35 | Editar
36 |
37 |
38 | Edit the contents of this item.
39 | Editar os conteúdos deste item.
40 |
41 |
42 | Not available
43 | Não disponível
44 |
45 |
46 | You do not have permission to edit this item.
47 | Você não possue permissão para editar este item.
48 |
49 |
50 | Move
51 | Mover
52 |
53 |
54 | Move this item to another location.
55 | Mover este item para outro local.
56 |
57 |
58 | You do not have permission to move this item to another location.
59 | Você não possue permissão para mover este para outro local.
60 |
61 |
62 | Remove
63 | Remover
64 |
65 |
66 | Remove this item.
67 | Remover este item.
68 |
69 |
70 | You do not have permission to remove this item.
71 | Você não possue permissão para remover este item.
72 |
73 |
74 | Preview
75 | Pré-visualizar
76 |
77 |
78 | New translation
79 | Nova tradução
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 | Usuário atual
87 |
88 |
89 | Change name, email, password, etc.
90 | Mudar nome, email, senha, etc.
91 |
92 |
93 | Change information
94 | Mudar informação
95 |
96 |
97 | Change user info
98 | Mudar informação de usuário
99 |
100 |
101 | Change password for <%username>.
102 | Mudar senha para <%username>.
103 |
104 |
105 | Change password
106 | Mudar senha
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 | Existe %basket_count item na cesta de compras.
111 |
112 |
113 | Shopping basket (%basket_count)
114 | Cesta de compras (%basket_count)
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 | Existem %basket_count itens na cesta de compras.
119 |
120 |
121 | Logout from the system.
122 | Sair do sistema.
123 |
124 |
125 | Logout
126 | Sair
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Your account information
133 | Informações da sua conta
134 |
135 |
136 | Email
137 | Email
138 |
139 |
140 |
141 | kernel/user
142 |
143 | User
144 | Usuário
145 |
146 |
147 | Forgot password
148 | Esqueci minha senha
149 |
150 |
151 | Change password
152 | Mudar senha
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 | Informações do cadastro
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Expiração de senha
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | O tempo de vida da senha deve ser um número inteiro >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | O tempo de notificação de expiração da senha deve ser um número inteiro >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | A senha não coincide com a regra de validação.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Valor incorreto para o campo updatechildren
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Regex de Validação
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Tempo de vida da senha (DIAS)
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Notificação de Expiração (SEGUNDOS)
199 |
200 |
201 | Current password status:
202 | Status atual da senha:
203 |
204 |
205 | expired
206 | expirada
207 |
208 |
209 | active
210 | ativa
211 |
212 |
213 | Update children nodes?
214 | Atualizar nós filhos?
215 |
216 |
217 | undefined
218 | indefinido
219 |
220 |
221 | Password status
222 | Status da senha
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Atualização de nós filhos pendente, será feito em poucos minutos...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Trocar senha de usuario
234 |
235 |
236 | Please retype your old password.
237 | Insira sua senha antiga.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | As novas senhas não coincidem, por favor redigite as novas senhas.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | A senha não é válida, por favor redigite sua nova senha.
246 |
247 |
248 | Password successfully updated.
249 | A senha foi modificada com sucesso.
250 |
251 |
252 | Old password
253 | Senha antiga
254 |
255 |
256 | New password
257 | Nova senha
258 |
259 |
260 | Retype password
261 | Redigite a senha
262 |
263 |
264 | OK
265 | OK
266 |
267 |
268 | Cancel
269 | Cancelar
270 |
271 |
272 | Your password is about to expire
273 | Sua senha está prestes a expirar
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl sua senha está prestes a expirar
278 |
279 |
280 | New password must be different from the old one. Please choose another password.
281 | A nova senha deve ser diferente da antiga. Por favor, escolha outra senha.
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
288 | Um e-mail foi enviado para o endereço de e-mail %1. O e-mail contém um link no qual você deve clicar para confirmar que o usuário correto está recebendo a nova senha.
289 |
290 |
291 | There is no registered user with that email address.
292 | Não existe nenhum usuário registrado com esse endereço de e-mail.
293 |
294 |
295 | The password has been changed successfully.
296 | A senha foi modificada com sucesso.
297 |
298 |
299 | The passwords do not match. Please, be sure to enter the same password in both fields.
300 | As novas senhas não são idênticas. Por favor, confira se as novas senhas são idênticas.
301 |
302 |
303 | The new password is invalid, please choose new one.
304 | A nova senha é inválida, por favor escolha uma nova.
305 |
306 |
307 | Enter your desired new password in the form below.
308 | Informe sua nova senha no formulário a seguir.
309 |
310 |
311 | Password
312 | Senha
313 |
314 |
315 | Password Confirm
316 | Confirmação de senha
317 |
318 |
319 | Change password
320 | Mudar senha
321 |
322 |
323 | The key is invalid or has been used.
324 | A chave é inválida ou já foi utilizada.
325 |
326 |
327 | Have you forgotten your password?
328 | Esqueceu sua senha?
329 |
330 |
331 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
332 | Se você esqueceu sua senha, uma nova pode ser gerada. Digite seu endereço de e-mail e uma nova senha será enviada a você.
333 |
334 |
335 | Email
336 | Email
337 |
338 |
339 | Generate new password
340 | Gerar nova senha
341 |
342 |
343 | %siteurl forgot password
344 | %siteurl senha esquecida
345 |
346 |
347 | Click here to set your new password
348 | Clique aqui para definir sua nova senha
349 |
350 |
351 | This link is valid until %1, after that time you should generate a new one.
352 | Este link é válido até %1, após esse prazo você deve gerar um novo.
353 |
354 |
355 | Choose a new password
356 | Escolha uma nova senha
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/cro-HR/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 | Pregled i upravljanje (kopiranje, brisanje itd.) verzija ovog objekta.
9 |
10 |
11 | Manage versions
12 | Upravljanje verzijama
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 | Promijenjeno
20 |
21 |
22 | Node ID
23 | ID čvora
24 |
25 |
26 | Object ID
27 | ID objekta
28 |
29 |
30 | Another language
31 | Drugi jezik
32 |
33 |
34 | Edit
35 | Uredi
36 |
37 |
38 | Edit the contents of this item.
39 | Uredi sadržaj ove stavke.
40 |
41 |
42 | Not available
43 | Nije dostpuno
44 |
45 |
46 | You do not have permission to edit this item.
47 | Nemate dozvolu za uređivanje ove stavke.
48 |
49 |
50 | Move
51 | Premjesti
52 |
53 |
54 | Move this item to another location.
55 | Premjesti ovu stavku na drugu lokaciju.
56 |
57 |
58 | You do not have permission to move this item to another location.
59 | Nemate dozbolu za premještanje ove stavke na drugu lokaciju.
60 |
61 |
62 | Remove
63 | Ukloni
64 |
65 |
66 | Remove this item.
67 | Ukloni ovu stavku.
68 |
69 |
70 | You do not have permission to remove this item.
71 | Nemate dozvolu za uklanjanje ove stavke.
72 |
73 |
74 | Preview
75 | Pregled
76 |
77 |
78 | New translation
79 | Novi prijevod
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 | Trenutni korisnik
87 |
88 |
89 | Change name, email, password, etc.
90 | Promijeni ime, email, lozinku itd.
91 |
92 |
93 | Change information
94 | Promijeni informacije
95 |
96 |
97 | Change user info
98 | Promijeni informacije o korisniku
99 |
100 |
101 | Change password for <%username>.
102 | Promijeni lozinku za <%username>.
103 |
104 |
105 | Change password
106 | Promijeni lozinku
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 | Postoji %basket_count stavki u košarici.
111 |
112 |
113 | Shopping basket (%basket_count)
114 | Košarica (%basket_count)
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 | Postoji %basket_count stavki u košarici.
119 |
120 |
121 | Logout from the system.
122 | Odjavi se iz sustava.
123 |
124 |
125 | Logout
126 | Odjava
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Your account information
133 | Informacije o vašem korisničkom računu
134 |
135 |
136 | Email
137 | Email
138 |
139 |
140 |
141 | kernel/user
142 |
143 | User
144 | Korisnik
145 |
146 |
147 | Forgot password
148 | Zaboravljena lozinka
149 |
150 |
151 | Change password
152 | Promijeni lozinku
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 | Informacije o registraciji
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Istjecanje lozinke
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | Vrijeme valjanosti lozinke mora biti cijeli broj >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | Vrijeme za obavijest o valjanosti lozinke mora biti cijeli broj >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | Lozinka ne odgovara pravilima.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Kriva vrijednost u updatechildren polju
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Regularni izraz za validaciju
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Valjanost lozinke (U DANIMA)
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Obavijest o valjanosti (U SEKUNDAMA)
199 |
200 |
201 | Current password status:
202 | Trenutni status lozinke:
203 |
204 |
205 | expired
206 | istekla
207 |
208 |
209 | active
210 | aktivna
211 |
212 |
213 | Update children nodes?
214 | Osvježiti podređene čvorove?
215 |
216 |
217 | undefined
218 | nedefinirano
219 |
220 |
221 | Password status
222 | Status lozinke
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Osvježavanje podređenih čvorova je u tijeku, bit će gotovo za par minuta...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Promijeni lozinku za korisnika
234 |
235 |
236 | Please retype your old password.
237 | Ponovno unesite vašu staru lozinku.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | Lozinka nije dobro unesena, molimo ponovno unesite vašu novu lozinku.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | Lozinka nije validirana, molimo ponovno unesite vašu novu lozinku.
246 |
247 |
248 | New password must be different from the old one. Please choose another password.
249 | Nova lozinka mora biti različita od stare. Odaberite drugu lozinku.
250 |
251 |
252 | Password successfully updated.
253 | Lozinka uspješno promijenjena.
254 |
255 |
256 | Old password
257 | Stara lozinka
258 |
259 |
260 | New password
261 | Nova lozinka
262 |
263 |
264 | Retype password
265 | Ponovno unesite lozinku
266 |
267 |
268 | OK
269 | OK
270 |
271 |
272 | Cancel
273 | Odustani
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl vaša lozinka uskoro ističe
278 |
279 |
280 | Your password is about to expire
281 | Vaša lozinka uskoro ističe
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | Click here to set your new password
288 | Kliknite ovdje za postavljanje nove lozinke
289 |
290 |
291 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
292 | Email je poslan na email adresu %1. Email sadrži link na koji trebate kliknuti da možemo potvrditi da ispravan korisnik dobija novu lozinku.
293 |
294 |
295 | There is no registered user with that email address.
296 | Ne postoji korisnik s tom email adresom.
297 |
298 |
299 | The password has been changed successfully.
300 | Lozinka je uspješno promijenjena.
301 |
302 |
303 | The passwords do not match. Please, be sure to enter the same password in both fields.
304 | Lozinke se ne podudaraju. Molimo unesite istu lozinku u oba polja.
305 |
306 |
307 | The new password is invalid, please choose new one.
308 | Nova lozinka je neispravna, molimo odaberite novu.
309 |
310 |
311 | Choose a new password
312 | Odaberite novu lozinku
313 |
314 |
315 | Enter your desired new password in the form below.
316 | Unesite željenu lozinku u donju formu.
317 |
318 |
319 | Password
320 | Lozinka
321 |
322 |
323 | Password Confirm
324 | Potvrda lozinke
325 |
326 |
327 | Change password
328 | Promjena lozinke
329 |
330 |
331 | The key is invalid or has been used.
332 | Ključ je neispravan ili je već iskorišten.
333 |
334 |
335 | Have you forgotten your password?
336 | Jeste li zaboravili vašu lozinku?
337 |
338 |
339 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
340 | Ako ste zaboravili vašu lozinku, možemo vam generirati novu. Sve što trebate napraviti je upisati vašu email adresu i kreirat ćemo novu lozinku za vas.
341 |
342 |
343 | Email
344 | Email
345 |
346 |
347 | Generate new password
348 | Generiraj novu lozinku
349 |
350 |
351 | %siteurl forgot password
352 | %siteurl zaboravljena lozinka
353 |
354 |
355 | This link is valid until %1, after that time you should generate a new one.
356 | Ovaj link je ispravan do %1, nakon toga morate generirati novu lozinku.
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/esl-ES/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 |
9 |
10 |
11 | Manage versions
12 |
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 |
20 |
21 |
22 | Node ID
23 |
24 |
25 |
26 | Object ID
27 |
28 |
29 |
30 | Another language
31 |
32 |
33 |
34 | Edit
35 |
36 |
37 |
38 | Edit the contents of this item.
39 |
40 |
41 |
42 | Not available
43 |
44 |
45 |
46 | Move
47 |
48 |
49 |
50 | Move this item to another location.
51 |
52 |
53 |
54 | Remove
55 |
56 |
57 |
58 | Remove this item.
59 |
60 |
61 |
62 | Preview
63 |
64 |
65 |
66 | You do not have permission to edit this item.
67 |
68 |
69 |
70 | You do not have permission to move this item to another location.
71 |
72 |
73 |
74 | You do not have permission to remove this item.
75 |
76 |
77 |
78 | New translation
79 |
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 |
87 |
88 |
89 | Change name, email, password, etc.
90 |
91 |
92 |
93 | Change information
94 |
95 |
96 |
97 | Change user info
98 |
99 |
100 |
101 | Change password for <%username>.
102 |
103 |
104 |
105 | Change password
106 | Cambiar contraseña
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 |
111 |
112 |
113 | Shopping basket (%basket_count)
114 |
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 |
119 |
120 |
121 | Logout from the system.
122 |
123 |
124 |
125 | Logout
126 |
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Email
133 | Correo electrónico
134 |
135 |
136 | Your account information
137 |
138 |
139 |
140 |
141 | kernel/user
142 |
143 | Change password
144 | Cambiar contraseña
145 |
146 |
147 | User
148 |
149 |
150 |
151 | Forgot password
152 |
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 |
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Caducidad de Contraseña
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | El tiempo de vida de la contraseña debe ser un número >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | El tiempo de notificación de expiración debe ser un número >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | La contraseña no respeta la regla de validación.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Valor incorrecto en el campo updatechildren
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Regexp de Validación
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Caducidad de la Contraseña (DÍAS)
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Notificación de Expiración (SEGUNDOS)
199 |
200 |
201 | Current password status:
202 | Estado actual de la contraseña:
203 |
204 |
205 | expired
206 | expirada
207 |
208 |
209 | active
210 | activa
211 |
212 |
213 | Update children nodes?
214 | ¿Actualizar nodos hijos?
215 |
216 |
217 | undefined
218 | no definido
219 |
220 |
221 | Password status
222 | Estado de la contraseña
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Actualización de hijos pendiente, será ejecutada en pocos minutos...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Cambio de contraseña de usuario
234 |
235 |
236 | Please retype your old password.
237 | Por favor, reescribe tu contraseña antigua.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | Las contraseñas no coinciden, por favor reescribe tu nueva contraseña.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | La contraseña no supera la validación, por favor reescribe tu nueva contraseña.
246 |
247 |
248 | Password successfully updated.
249 | Contraseña actualizada correctamente.
250 |
251 |
252 | Old password
253 | Contraseña antigua
254 |
255 |
256 | New password
257 | Nueva contraseña
258 |
259 |
260 | Retype password
261 | Reescribe la contraseña
262 |
263 |
264 | OK
265 | OK
266 |
267 |
268 | Cancel
269 | Cancelar
270 |
271 |
272 | Your password is about to expire
273 | Tu contraseña está a punto de caducar
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl tu contraseña está a punto de caducar
278 |
279 |
280 | New password must be different from the old one. Please choose another password.
281 | La nueva contraseña ha de ser diferente de la antigua. Por favor escoge otra contraseña.
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
288 | Un correo electrónico ha sido enviado a la siguiente dirección: %1. Este correo contiene un enlace que debes pulsar para poder cambiar la contraseña.
289 |
290 |
291 | There is no registered user with that email address.
292 | No hay ningún usuario registrado con esa dirección de correo electrónico.
293 |
294 |
295 | The password has been changed successfully.
296 | La contraseña ha sido cambiada correctamente.
297 |
298 |
299 | The passwords do not match. Please, be sure to enter the same password in both fields.
300 | Las contraseñas no coinciden. Por favor, asegúrate que introduces la misma contraseña en ambos campos.
301 |
302 |
303 | The new password is invalid, please choose new one.
304 | La nueva contraseña es inválida, por favor escoge una nueva.
305 |
306 |
307 | Enter your desired new password in the form below.
308 | Introduce tu nueva contraseña en el siguiete formulario.
309 |
310 |
311 | Password
312 | Contraseña
313 |
314 |
315 | Password Confirm
316 | Confirmación de la Contraseña
317 |
318 |
319 | Change password
320 | Cambiar contraseña
321 |
322 |
323 | The key is invalid or has been used.
324 | La clave no es válida o ha sido utilizada.
325 |
326 |
327 | Have you forgotten your password?
328 | ¿Has olvidado tu contraseña?
329 |
330 |
331 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
332 | Si has olvidado tu contraseña podemos generar una nueva para ti. Todo lo que necesitas hacer es introducir tu dirección de correo electrónico y nosotros crearemos una contraseña para ti.
333 |
334 |
335 | Email
336 | Correo electrónico
337 |
338 |
339 | Generate new password
340 | Generar nueva contraseña
341 |
342 |
343 | %siteurl forgot password
344 | %siteurl contraseña olvidada
345 |
346 |
347 | Click here to set your new password
348 | Pulsa aquí para fijar tu nueva contraseña
349 |
350 |
351 | This link is valid until %1, after that time you should generate a new one.
352 | Este enlace es válido hasta %1, tras ese tiempo tendrás que generar uno nuevo.
353 |
354 |
355 | Choose a new password
356 | Escoge una nueva contraseña
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/ita-IT/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 | Guarda e gestisci (copia, elimina, ecc.) le versioni di quest'oggetto.
9 |
10 |
11 | Manage versions
12 | Gestisci versioni
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 | Ultima modifica
20 |
21 |
22 | Node ID
23 | ID nodo
24 |
25 |
26 | Object ID
27 | ID oggetto
28 |
29 |
30 | Another language
31 | Un'altra lingua
32 |
33 |
34 | Edit
35 | Modifica
36 |
37 |
38 | Edit the contents of this item.
39 | Modifica i contenuti di quest'elemento.
40 |
41 |
42 | Not available
43 | Non disponibile
44 |
45 |
46 | You do not have permission to edit this item.
47 | Non sei abilitato a modifcare quest'elemento.
48 |
49 |
50 | Move
51 | Sposta
52 |
53 |
54 | Move this item to another location.
55 | Sposta quest'elemento in un'altra collocazione.
56 |
57 |
58 | You do not have permission to move this item to another location.
59 | Non sei abilitato a spostare quest'elemento in un'altra collocazione.
60 |
61 |
62 | Remove
63 | Elimina
64 |
65 |
66 | Remove this item.
67 | Elimina quest'elemento.
68 |
69 |
70 | You do not have permission to remove this item.
71 | Non sei abilitato ad eliminare quest'elemento.
72 |
73 |
74 | Preview
75 | Anteprima
76 |
77 |
78 | New translation
79 | Nuova traduzione
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 | Utente attuale
87 |
88 |
89 | Change name, email, password, etc.
90 | Cambia nome, email, password, ecc.
91 |
92 |
93 | Change information
94 | Cambia informazioni
95 |
96 |
97 | Change user info
98 | Cambia info utente
99 |
100 |
101 | Change password for <%username>.
102 | Cambia password per <%username>.
103 |
104 |
105 | Change password
106 | Cambia password
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 | Vi è %basket_count elemento nel carrello.
111 |
112 |
113 | Shopping basket (%basket_count)
114 | Carrello (%basket_count)
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 | Vi sono %basket_count elementi nel carrello.
119 |
120 |
121 | Logout from the system.
122 | Logout dal sistema.
123 |
124 |
125 | Logout
126 | Logout
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Your account information
133 | Informazioni sul tuo account
134 |
135 |
136 | Email
137 | Email
138 |
139 |
140 |
141 | kernel/user
142 |
143 | User
144 | Utente
145 |
146 |
147 | Forgot password
148 | Password dimenticata
149 |
150 |
151 | Change password
152 | Cambia password
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 | Info registrazione
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Scadenza password
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | La durata della password dev'essere un intero >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | L'intervallo di tempo di notifica della scadenza dev'essere un intero >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | La password non coincide con la validazione.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Valore sbagliato nel campo aggiorna figli
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Validazione Regexp
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Durata password (GIORNI)
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Notifica scadenza (SECONDI)
199 |
200 |
201 | Current password status:
202 | Stato password attuale:
203 |
204 |
205 | expired
206 | scaduta
207 |
208 |
209 | active
210 | attiva
211 |
212 |
213 | Update children nodes?
214 | Aggiornare i nodi figli?
215 |
216 |
217 | undefined
218 | indefinito
219 |
220 |
221 | Password status
222 | Stato password
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Aggiornamento figli in attesa, verrà eseguito in pochi minuti...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Cambia la password per l'utente
234 |
235 |
236 | Please retype your old password.
237 | Sei pregato di reinserire la tua vecchia password.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | Le password non coincidono, sei pregato di reinserire la tua nuova password.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | La password non è valida, sei pregato di reinserire la tua nuova password.
246 |
247 |
248 | New password must be different from the old one. Please choose another password.
249 | La nuova password dev'essere diversa dalla vecchia. Sei pregato di scegliere un'altra password.
250 |
251 |
252 | Password successfully updated.
253 | Aggiornamento password riuscito.
254 |
255 |
256 | Old password
257 | Vecchia password
258 |
259 |
260 | New password
261 | Nuova password
262 |
263 |
264 | Retype password
265 | Reinserisci la password
266 |
267 |
268 | OK
269 | OK
270 |
271 |
272 | Cancel
273 | Annulla
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl la tua password sta per scadere
278 |
279 |
280 | Your password is about to expire
281 | La tua password sta per scadere
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | Click here to set your new password
288 | Clicca qui per impostare la tua nuova password
289 |
290 |
291 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
292 | E' stata inviata un'email al seguente indirizzo email: %1. Quest'email contiene un link che devi cliccare per darci la conferma che l'utente giusto ha ricevuto la nuova password.
293 |
294 |
295 | There is no registered user with that email address.
296 | Non esiste alcun utente registrato con quest'indirizzo email.
297 |
298 |
299 | The password has been changed successfully.
300 | Modifica password riuscita.
301 |
302 |
303 | The passwords do not match. Please, be sure to enter the same password in both fields.
304 | Le password non coincidono. Sei pregato di verificare di aver inserito la stessa password in entrambi i campi.
305 |
306 |
307 | The new password is invalid, please choose new one.
308 | La nuova password non è valida, sei pregato di sceglierne un'altra.
309 |
310 |
311 | Choose a new password
312 | Scegli una nuova password
313 |
314 |
315 | Enter your desired new password in the form below.
316 | Inserisci la nuova password scelta nel campo sottostante.
317 |
318 |
319 | Password
320 | Password
321 |
322 |
323 | Password Confirm
324 | Conferma password
325 |
326 |
327 | Change password
328 | Cambia password
329 |
330 |
331 | The key is invalid or has been used.
332 | La chiave non è valida o è stata usata.
333 |
334 |
335 | Have you forgotten your password?
336 | Hai dimenticato la tua password?
337 |
338 |
339 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
340 | Se hai dimenticato la tua password possiamo generartene un'altra. Devi solo inserire il tuo indirizzo email e noi ti creeremo una nuova password.
341 |
342 |
343 | Email
344 | Email
345 |
346 |
347 | Generate new password
348 | Genera una nuova password
349 |
350 |
351 | %siteurl forgot password
352 | %siteurl password dimenticata
353 |
354 |
355 | This link is valid until %1, after that time you should generate a new one.
356 | Questo link è valido fino a %1, dopo questo termine dovrai generarne un'altra.
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/cat-ES/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 |
9 |
10 |
11 | Manage versions
12 |
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 |
20 |
21 |
22 | Node ID
23 |
24 |
25 |
26 | Object ID
27 |
28 |
29 |
30 | Another language
31 |
32 |
33 |
34 | Edit
35 |
36 |
37 |
38 | Edit the contents of this item.
39 |
40 |
41 |
42 | Not available
43 |
44 |
45 |
46 | Move
47 |
48 |
49 |
50 | Move this item to another location.
51 |
52 |
53 |
54 | Remove
55 |
56 |
57 |
58 | Remove this item.
59 |
60 |
61 |
62 | Preview
63 |
64 |
65 |
66 | You do not have permission to edit this item.
67 |
68 |
69 |
70 | You do not have permission to move this item to another location.
71 |
72 |
73 |
74 | You do not have permission to remove this item.
75 |
76 |
77 |
78 | New translation
79 |
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 |
87 |
88 |
89 | Change name, email, password, etc.
90 |
91 |
92 |
93 | Change information
94 |
95 |
96 |
97 | Change user info
98 |
99 |
100 |
101 | Change password for <%username>.
102 |
103 |
104 |
105 | Change password
106 | Canviar contrasenya
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 |
111 |
112 |
113 | Shopping basket (%basket_count)
114 |
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 |
119 |
120 |
121 | Logout from the system.
122 |
123 |
124 |
125 | Logout
126 |
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Email
133 | Correu electrònic
134 |
135 |
136 | Your account information
137 |
138 |
139 |
140 |
141 | kernel/user
142 |
143 | Change password
144 | Canviar contrasenya
145 |
146 |
147 | User
148 |
149 |
150 |
151 | Forgot password
152 |
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 |
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Caducitat de Contrasenya
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | El temps de vida de la contrasenya ha de ser un nombre >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | El temps de notificació d'expiració ha de ser un nombre >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | La contrasenya no cumpleix la regla de validació.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Valor incorrecte al camp updatechildren
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Regexp de validació
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Caducitat de la contrasenya (DIES)
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Notificació d'expiració (SEGONS)
199 |
200 |
201 | Current password status:
202 | Estat actual de la contrasenya:
203 |
204 |
205 | expired
206 | caducada
207 |
208 |
209 | active
210 | activa
211 |
212 |
213 | Update children nodes?
214 | Actualitzar fills del node?
215 |
216 |
217 | undefined
218 | no definit
219 |
220 |
221 | Password status
222 | Estat de la contrasenya
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Actualització dels fills pendents, serà realitzada en pocs minuts...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Canvia la contrasenya del usuari
234 |
235 |
236 | Please retype your old password.
237 | Si-us-plau reescriu la contrasenya antiga.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | Les contrasenyes no coincideixen, si-us-plau reescriu la teva nova contrasenya.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | La contrasenya no supera la validació, si-us-plau reescriu la nova contrasenya.
246 |
247 |
248 | Password successfully updated.
249 | Contrasenya actualitzada correctament.
250 |
251 |
252 | Old password
253 | Contrasenya antiga
254 |
255 |
256 | New password
257 | Nova contrasenya
258 |
259 |
260 | Retype password
261 | Reescriu la contrasenya
262 |
263 |
264 | OK
265 | D'acord
266 |
267 |
268 | Cancel
269 | Cancel·lar
270 |
271 |
272 | Your password is about to expire
273 | La teva contrasenya és a punt de caducar
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl la teva contrasenya és a punt de caducar
278 |
279 |
280 | New password must be different from the old one. Please choose another password.
281 | La nova contrasenya ha de ser diferent de l'antiga. Si-us-plau tria una altra contrasenya.
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
288 | S'ha enviat un correu electrònic a la següent adreça: %1. Aquest correu conté un enllaç amb el que accediràs al formulari per fixar una nova contrasenya.
289 |
290 |
291 | There is no registered user with that email address.
292 | No hi ha cap usuari registrat amb aquesta adreça de correu electrònic.
293 |
294 |
295 | The password has been changed successfully.
296 | La contrasenya s'ha canviat correctament.
297 |
298 |
299 | The passwords do not match. Please, be sure to enter the same password in both fields.
300 | Les contrasenyes no coincideixen. Si-us-plau, assegura't d'introduir la mateixa contrasenya als dos camps.
301 |
302 |
303 | The new password is invalid, please choose new one.
304 | La nova contrasenya no és vàlida, si-us-plau tria una de nova.
305 |
306 |
307 | Enter your desired new password in the form below.
308 | Introdueix la nova contrasenya al següent formulari.
309 |
310 |
311 | Password
312 | Contrasenya
313 |
314 |
315 | Password Confirm
316 | Confirmar Contrasenya
317 |
318 |
319 | Change password
320 | Canviar contrasenya
321 |
322 |
323 | The key is invalid or has been used.
324 | La clau no és vàlida o ha estat utilitzada.
325 |
326 |
327 | Have you forgotten your password?
328 | Has oblidat la teva contrasenya?
329 |
330 |
331 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
332 | Si has oblidat la teva contrasenya nosaltres podem generar una de nova per tu. Tot el que necessites és introduir la teva adreça de correu electrònic i crearem una nova contrasenya per tu.
333 |
334 |
335 | Email
336 | Correu electrònic
337 |
338 |
339 | Generate new password
340 | Generar contrasenya
341 |
342 |
343 | %siteurl forgot password
344 | %siteurl contrasenya oblidada
345 |
346 |
347 | Click here to set your new password
348 | Fes clic aqui per fixar la teva nova contrasenya
349 |
350 |
351 | This link is valid until %1, after that time you should generate a new one.
352 | Aquest enllaç és vàlid fins %1, després d'aquest temps hauràs de generar un de nou.
353 |
354 |
355 | Choose a new password
356 | Tria una nova contrasenya
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/translations/fre-FR/translation.ts:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | design/admin/content/edit
6 |
7 | View and manage (copy, delete, etc.) the versions of this object.
8 | Afficher et gérer (copier, supprimer, etc.) les versions de cet objet.
9 |
10 |
11 | Manage versions
12 | Gérer les versions
13 |
14 |
15 |
16 | design/admin/node/view/full
17 |
18 | Last modified
19 | Dernière modification
20 |
21 |
22 | Node ID
23 | ID du nœud
24 |
25 |
26 | Object ID
27 | ID de l'objet
28 |
29 |
30 | Another language
31 | Autre langue
32 |
33 |
34 | Edit
35 | Modifier
36 |
37 |
38 | Edit the contents of this item.
39 | Modifier le contenu de cet éléments.
40 |
41 |
42 | Not available
43 | Non disponible
44 |
45 |
46 | Move
47 | Déplacer
48 |
49 |
50 | Move this item to another location.
51 | Déplacer cet élément vers un autre emplacement.
52 |
53 |
54 | Remove
55 | Supprimer
56 |
57 |
58 | Remove this item.
59 | Supprimer cet élément.
60 |
61 |
62 | Preview
63 | Prévisualisation
64 |
65 |
66 | You do not have permission to edit this item.
67 | Vous n'avez pas le droit de modifier cet élément.
68 |
69 |
70 | You do not have permission to move this item to another location.
71 | Vous n'avez pas le droit de déplacer cet élément vers un autre emplacement.
72 |
73 |
74 | You do not have permission to remove this item.
75 | Vous n'avez pas le droit de supprimer cet élément.
76 |
77 |
78 | New translation
79 | Nouvelle traduction
80 |
81 |
82 |
83 | design/admin/pagelayout
84 |
85 | Current user
86 | Utilisateur identifié
87 |
88 |
89 | Change name, email, password, etc.
90 | Modifier le nom, l'adresse courriel, le mot de passe, etc.
91 |
92 |
93 | Change information
94 | Modifier les informations
95 |
96 |
97 | Change user info
98 | Modifier les informations personnelles
99 |
100 |
101 | Change password for <%username>.
102 | Changer le mot de passe de <%username>.
103 |
104 |
105 | Change password
106 | Modifier le mot de passe
107 |
108 |
109 | There is %basket_count item in the shopping basket.
110 | Le panier comporte %basket_count éléments.
111 |
112 |
113 | Shopping basket (%basket_count)
114 | Panier (%basket_count)
115 |
116 |
117 | There are %basket_count items in the shopping basket.
118 | Le panier comporte %basket_count éléments.
119 |
120 |
121 | Logout from the system.
122 | Quitter.
123 |
124 |
125 | Logout
126 | Fermeture de session
127 |
128 |
129 |
130 | design/standard/user/forgotpassword
131 |
132 | Email
133 | Courriel
134 |
135 |
136 | Your account information
137 | Les informations sur votre compte
138 |
139 |
140 |
141 | kernel/user
142 |
143 | User
144 | Utilisateur
145 |
146 |
147 | Change password
148 | Modifier mon mot de passe
149 |
150 |
151 | Forgot password
152 | Mot de passe oublié
153 |
154 |
155 |
156 | kernel/user/register
157 |
158 | Registration info
159 | Informations d'inscription
160 |
161 |
162 |
163 | mbpaex/classes/datatypes
164 |
165 | Password Expiration
166 | Datatype name
167 | Expiration de mot de passe
168 |
169 |
170 | The password lifetime must be an integer >= 0
171 | La durée de vie du mot de passe doit être un entier >= 0
172 |
173 |
174 | The expiration notification time must be an integer >= 86400
175 | Le délai de notification d'expiration doit être un entier >= 86400
176 |
177 |
178 | The password doesn't match the validation rule.
179 | Le mot de passe ne respecte pas la règle de validation.
180 |
181 |
182 | Wrong value in updatechildren field
183 | Valeur incorrecte dans le champ updatechildren
184 |
185 |
186 |
187 | mbpaex/content/datatype
188 |
189 | Validation Regexp
190 | Expression régulière de validation
191 |
192 |
193 | Password LifeTime (DAYS)
194 | Durée de vie du mot de passe ( JOURS )
195 |
196 |
197 | Expiration Notification (SECONDS)
198 | Délai de notification d'expiration ( SECONDES )
199 |
200 |
201 | Current password status:
202 | Satut actuel du mot de passe:
203 |
204 |
205 | expired
206 | expiré
207 |
208 |
209 | active
210 | actif
211 |
212 |
213 | Update children nodes?
214 | Mettre à jour les nœuds enfants ?
215 |
216 |
217 | undefined
218 | indéfini
219 |
220 |
221 | Password status
222 | Statut du mot de passe
223 |
224 |
225 | Children update pending, will be done in a few minutes...
226 | Mise à jour des nœuds enfants en attente, sera effectuée dans quelques minutes...
227 |
228 |
229 |
230 | mbpaex/userpaex
231 |
232 | Change password for user
233 | Changement de mot de passe pour l'utilisateur
234 |
235 |
236 | Please retype your old password.
237 | Entrez à nouveau votre ancien mot de passe.
238 |
239 |
240 | Password didn't match, please retype your new password.
241 | Les mots de passe saisis ne coïncident pas, veuillez entrer à nouveau votre nouveau mot de passe.
242 |
243 |
244 | Password didn't validate, please retype your new password.
245 | Le mot de passe n'a pas pu être validé, veuillez entrer à nouveau votre nouveau mot de passe.
246 |
247 |
248 | Password successfully updated.
249 | Mot de passe correctement mis à jour.
250 |
251 |
252 | Old password
253 | Ancien mot de passe
254 |
255 |
256 | New password
257 | Nouveau mot de passe
258 |
259 |
260 | Retype password
261 | Saisir le mot de passe à nouveau
262 |
263 |
264 | OK
265 | OK
266 |
267 |
268 | Cancel
269 | Annuler
270 |
271 |
272 | Your password is about to expire
273 | Votre mot de passe va bientôt expirer
274 |
275 |
276 | %siteurl your password is about to expire
277 | %siteurl votre mot de passe va bientôt expirer
278 |
279 |
280 | New password must be different from the old one. Please choose another password.
281 | Le nouveau mot de passe doit être différent de l'ancien. Veuillez choisir un autre mot de passe.
282 |
283 |
284 |
285 | mbpaex/userpaex/forgotpassword
286 |
287 | A mail has been sent to the following email address: %1. This email contains a link you need to click so that we can confirm that the correct user is getting the new password.
288 | Un courrier électronique a été envoyé à l'adresse suivante: %1. Ce courrier contient un lien sur lequel vous devez cliquer pour confirmer que le bon utilisateur reçoit le nouveau mot de passe.
289 |
290 |
291 | There is no registered user with that email address.
292 | Aucun utilisateur enregistré sous cette adresse électronique.
293 |
294 |
295 | The password has been changed successfully.
296 | Le mot de passe a été modifié avec succès.
297 |
298 |
299 | The passwords do not match. Please, be sure to enter the same password in both fields.
300 | Les mots de passe ne coïncident pas. Assurez-vous de saisir le même mot de passe dans les deux champs.
301 |
302 |
303 | The new password is invalid, please choose new one.
304 | Le nouveau mot de passe est invalide, veuillez en choisir un autre.
305 |
306 |
307 | Enter your desired new password in the form below.
308 | Saisissez votre nouveau mot de passe dans le formulaire ci-dessous.
309 |
310 |
311 | Password
312 | Mot de passe
313 |
314 |
315 | Password Confirm
316 | Confirmation du mot de passe
317 |
318 |
319 | Change password
320 | Changer de mot de passe
321 |
322 |
323 | The key is invalid or has been used.
324 | La clé est invalide ou a été utilisée.
325 |
326 |
327 | Have you forgotten your password?
328 | Vous avez oublié votre mot de passe?
329 |
330 |
331 | If you have forgotten your password we can generate a new one for you. All you need to do is to enter your email address and we will create a new password for you.
332 | Nous pouvons vous générer un nouveau mot de passe si vous l'avez oublié. Il vous suffit de saisir votre adresse email ci-dessous, et nous nous chargerons de vous créer un nouveau mot de passe.
333 |
334 |
335 | Email
336 | Adresse électronique
337 |
338 |
339 | Generate new password
340 | Générer le nouveau mot de passe
341 |
342 |
343 | %siteurl forgot password
344 | %siteurl mot de passe oublié
345 |
346 |
347 | Click here to set your new password
348 | Cliquer ici pour saisir un nouveau mot de passe
349 |
350 |
351 | This link is valid until %1, after that time you should generate a new one.
352 | Ce lien est valide jusqu'à %1, après quoi vous devrez en générer un nouveau.
353 |
354 |
355 | Choose a new password
356 | Choisissez un nouveau mot de passe
357 |
358 |
359 |
360 |
--------------------------------------------------------------------------------
/tests/classes/ezpaex_test.php:
--------------------------------------------------------------------------------
1 | setName( "eZ Password Expiry Unit Tests" );
20 | }*/
21 |
22 | /**
23 | * setUp():
24 | * - creates a PAEX object for the admin user
25 | **/
26 | public function setUp()
27 | {
28 | parent::setUp();
29 |
30 | $this->paexTime = time();
31 |
32 | $row = array( 'contentobject_id' => 14,
33 | 'passwordvalidationregexp' => '',
34 | 'passwordlifetime' => 3,
35 | 'expirationnotification' => eZPaEx::NOT_DEFINED,
36 | 'password_last_updated' => $this->paexTime,
37 | 'updatechildren' => 0,
38 | 'expirationnotification_sent' => 0 );
39 | $this->paex = new eZPaEx( $row );
40 |
41 | $this->paexINI = eZINI::instance( 'mbpaex.ini' );
42 | }
43 |
44 | /**
45 | * tearDown():
46 | * - deletes the admin PAEX object if it still exists
47 | **/
48 | public function tearDown()
49 | {
50 | parent::tearDown();
51 |
52 | // remove the PAEX object if it hasn't been removed by the test
53 | if ( eZPaEx::fetch( $this->paex->attribute( 'contentobject_id' ) ) )
54 | eZPaEx::removePaex( $this->paex->attribute( 'contentobject_id' ) );
55 | }
56 |
57 | /**
58 | * Unit test for eZPaEx::__construct()
59 | **/
60 | public function testeZPaEx()
61 | {
62 | $this->assertInstanceOf( 'eZPaEx', $this->paex );
63 |
64 | $this->assertEquals( 14, $this->paex->attribute( 'contentobject_id' ) );
65 | $this->assertEquals( '', $this->paex->attribute( 'passwordvalidationregexp' ) );
66 | $this->assertEquals( 3, $this->paex->attribute( 'passwordlifetime' ) );
67 | $this->assertEquals( eZPaEx::NOT_DEFINED, $this->paex->attribute( 'expirationnotification' ) );
68 | $this->assertEquals( $this->paexTime, $this->paex->attribute( 'password_last_updated' ) );
69 | $this->assertEquals( 0, $this->paex->attribute( 'updatechildren' ) );
70 | $this->assertEquals( 0, $this->paex->attribute( 'expirationnotification_sent' ) );
71 | }
72 |
73 | /**
74 | * Unit test for eZPaEx::create()
75 | **/
76 | public function testCreate()
77 | {
78 | // Create a user instance
79 | $user = self::createUser( __FUNCTION__ );
80 |
81 | // Create a paex instanced based on this user's content object ID
82 | $paex = eZPaEx::create( $user->attribute( 'contentobject_id' ) );
83 | $this->assertInstanceOf( 'eZPaEx', $paex );
84 | $this->assertEquals( $this->paexINI->variable( 'mbpaexSettings', 'PasswordValidationRegexp' ),
85 | $paex->attribute( 'passwordvalidationregexp' ),
86 | "Password validation regexp value doesn't match" );
87 | $this->assertEquals( $this->paexINI->variable( 'mbpaexSettings', 'DefaultPasswordLifeTime' ),
88 | $paex->attribute( 'passwordlifetime' ),
89 | "Password lifetime value doesn't match" );
90 | $this->assertEquals( $this->paexINI->variable( 'mbpaexSettings', 'ExpirationNotification' ),
91 | $paex->attribute( 'expirationnotification' ),
92 | "Password expiration notification value doesn't match" );
93 | $this->assertEquals( $user->attribute( 'contentobject_id' ),
94 | $paex->attribute( 'contentobject_id' ),
95 | "Paex contentobject ID doesn't match" );
96 | }
97 |
98 | /**
99 | * Unit test for eZPaEx::setInformation()
100 | **/
101 | public function testSetInformation()
102 | {
103 | $user = self::createUser( __FUNCTION__ );
104 |
105 | $paex = new eZPaEx( array() );
106 | $paex->setInformation(
107 | $contentObjectID = $user->attribute( 'id' ),
108 | $regexp = '',
109 | $passwordLifetime = 10,
110 | $expirationNotification = eZPaEx::NOT_DEFINED,
111 | $time = time(),
112 | $updateChildren = 0,
113 | $expirationNotificationSent = 1 );
114 |
115 | $this->assertEquals( $contentObjectID, $paex->attribute( 'contentobject_id' ),
116 | "attribute contentobject_id doesn't match" );
117 | $this->assertEquals( $regexp, $paex->attribute( 'passwordvalidationregexp' ),
118 | "attribute passwordvalidationregexp doesn't match" );
119 | $this->assertEquals( $passwordLifetime, $paex->attribute( 'passwordlifetime' ),
120 | "attribute passwordlifetime doesn't match" );
121 | $this->assertEquals( $expirationNotification, $paex->attribute( 'expirationnotification' ),
122 | "attribute expirationnotification doesn't match" );
123 | $this->assertEquals( $time, $paex->attribute( 'password_last_updated' ),
124 | "attribute password_last_updated doesn't match" );
125 | $this->assertEquals( $updateChildren, $paex->attribute( 'updatechildren' ),
126 | "attribute updatechildren doesn't match" );
127 | $this->assertEquals( $expirationNotificationSent, $paex->attribute( 'expirationnotification_sent' ),
128 | "attribute expirationnotification_sent doesn't match" );
129 | }
130 |
131 | /**
132 | * Unit test for eZPaEx::store()
133 | **/
134 | public function testStore()
135 | {
136 | $user = self::createUser( __FUNCTION__ );
137 | $contentObjectID = $user->attribute( 'id' );
138 | $paex = eZPaEx::create( $contentObjectID );
139 |
140 | // First try fetching the object from the database
141 | // @expected null
142 | $this->assertNull( eZPaEx::fetch( $contentObjectID ),
143 | "PaEx #$contentObjectID hasn't been stored yet, fetch() should have returned null" );
144 |
145 | // store, and try to fetch again
146 | $paex->store();
147 | $fetchedPaex = eZPaEx::fetch( $contentObjectID );
148 | $this->assertInstanceOf( 'eZPaEx', $fetchedPaex,
149 | "PaEx #$contentObjectID has been stored, fetch() should have returned the object" );
150 | }
151 |
152 | /**
153 | * Unit test for eZPaEx::removePaex()
154 | **/
155 | public function testRemovePaex()
156 | {
157 | $user = self::createUser( __FUNCTION__ );
158 | $paex = eZPaEx::create( $user->attribute( 'id' ) );
159 | $paex->store();
160 |
161 | $id = $paex->attribute( 'contentobject_id' );
162 | unset( $paex );
163 |
164 | // fetch again to be sure it is stored
165 | $this->assertInstanceOf( 'eZPaEx', eZPaEx::fetch( $id ),
166 | "eZPaEx::fetch() should have returned an object" );
167 |
168 | // remove, and check if fetch fails as expected
169 | eZPaEx::removePaex( $id );
170 | $this->assertEquals( null, eZPaEx::fetch( $id ),
171 | "eZPaEx::fetch() should have returned null as the object should no longer exist" );
172 | }
173 |
174 | /**
175 | * Unit test for eZPaEx::fetch()
176 | **/
177 | public function testFetch()
178 | {
179 | // Create a user
180 | $user = self::createUser( __FUNCTION__ );
181 | $contentObjectID = $user->attribute( 'id' );
182 |
183 | // Try fetching this user's ID. Should fail.
184 | $this->assertNull( eZPaEx::fetch( $contentObjectID ),
185 | "eZPaEx::fetch() should be null as the object hasn't been created yet" );
186 |
187 | // Create & store the PaEx
188 | eZPaEx::create( $contentObjectID )->store();
189 |
190 | // Try fetching it again
191 | $this->assertInstanceOf( 'eZPaEx', eZPaEx::fetch( $contentObjectID ) );
192 | }
193 |
194 | /**
195 | * Unit test for eZPaEx::isExpired
196 | *
197 | * @param int $passwordLifetime
198 | * @param int $passwordLastUpdated
199 | * @param bool $expected
200 | *
201 | * @dataProvider providerForTestIsExpired
202 | **/
203 | public function testIsExpired( $passwordLifetime, $passwordLastUpdated, $expected )
204 | {
205 | $this->paex->setAttribute( 'passwordlifetime', $passwordLifetime );
206 | $this->paex->setAttribute( 'password_last_updated', $passwordLastUpdated );
207 |
208 | $this->assertEquals( $expected, $this->paex->isExpired() );
209 | }
210 |
211 | /**
212 | * Unit test for eZPaEx::isUser()
213 | */
214 | public function testIsUser()
215 | {
216 | $this->assertTrue( $this->paex->isUser(), "PaEx object should have been a user" );
217 |
218 | $paex = new eZPaEx( array() );
219 | $this->assertFalse( $paex->isUser(), "PaEx object shouldn't have been a user" );
220 | }
221 |
222 | /**
223 | * Unit test for eZPaEx::hasRegexp
224 | */
225 | function testHasRegexp()
226 | {
227 | // No regexp on the default object
228 | $this->assertFalse( $this->paex->hasRegexp(), "PaEx object shouldn't have a regexp" );
229 |
230 | // Set a regexp and test again
231 | $this->paex->setAttribute( 'passwordvalidationregexp', '/^[a-z0-9]$/' );
232 | $this->assertTrue( $this->paex->hasRegexp(), "PaEx object should have a regexp" );
233 | }
234 |
235 | /**
236 | * Unit test for eZPaEx::hasLifeTime()
237 | */
238 | function testHasLifeTime()
239 | {
240 | $this->assertTrue( $this->paex->hasLifeTime(), "PaEx object should have a lifetime" );
241 |
242 | // Set lifetime to an empty value
243 | $this->paex->setAttribute( 'passwordlifetime', '' );
244 | $this->assertFalse( $this->paex->hasLifeTime(), "PaEx object shouldn't have a lifetime (empty string)" );
245 |
246 | // Set lifetime to the NOT_DEFINED constant
247 | $this->paex->setAttribute( 'passwordlifetime', eZPaEx::NOT_DEFINED );
248 | $this->assertFalse( $this->paex->hasLifeTime(), "PaEx object shouldn't have a lifetime (eZPaEx::NOT_DEFINED)" );
249 | }
250 |
251 | /**
252 | * Unit test for eZPaEx::hasNotification()
253 | */
254 | function testHasNotification()
255 | {
256 | // default object has expirationnotification set to eZPaEx::NOT_DEFINED
257 | $this->assertFalse( $this->paex->hasNotification(), "PaEx object should not have a lifetime" );
258 |
259 | // check with null
260 | $this->paex->setAttribute( 'expirationnotification', null );
261 | $this->assertFalse( $this->paex->hasNotification(), "PaEx object should not have a lifetime" );
262 |
263 | // check with empty string
264 | $this->paex->setAttribute( 'expirationnotification', '' );
265 | $this->assertFalse( $this->paex->hasNotification(), "PaEx object should not have a lifetime" );
266 |
267 | // check with an actual value
268 | $this->paex->setAttribute( 'expirationnotification', 172800 );
269 | $this->assertTrue( $this->paex->hasNotification(), "PaEx object should have a lifetime" );
270 | }
271 |
272 | /**
273 | * Unit test for eZPaEx::validatePassword()
274 | *
275 | * @dataProvider providerForTestValidatePassword
276 | */
277 | function testValidatePassword( $regexp, $expected, $password = 'publish' )
278 | {
279 | // The default object has an empty regexp, will always be valid
280 | $this->paex->setAttribute( 'passwordvalidationregexp', $regexp );
281 | if ( $expected === true )
282 | {
283 | $this->assertTrue( $this->paex->validatePassword( $password ) );
284 | }
285 | elseif ( $expected === false )
286 | {
287 | $this->assertFalse( $this->paex->validatePassword( $password ) );
288 | }
289 | else
290 | {
291 | $this->markTestSkipped( "Unknown value for \$expected" );
292 | }
293 | }
294 |
295 | /**
296 | * Data provider for testValidatePassword()
297 | *
298 | * @see eZPaExTest::testValidatePassword()
299 | */
300 | public static function providerForTestValidatePassword()
301 | {
302 | return array(
303 | // empty values
304 | array( '', true ),
305 | array( null, true ),
306 | array( eZPaEx::NOT_DEFINED, true ),
307 |
308 | // test different regexp forms
309 | array( '^[0-9a-z]+$', true ),
310 | array( '/^[0-9a-z]+$/', true),
311 |
312 | // a few rejected passwords
313 | array( '^[0-9a-z]+$', false, 'my_password' ),
314 | array( '^[0-9]+$', false, '#@~&' )
315 | );
316 | }
317 |
318 | /**
319 | * dataProvider for testIsExpired()
320 | **/
321 | public static function providerForTestIsExpired()
322 | {
323 | return array(
324 | // undefined password lifetime
325 | array( eZPaEx::NOT_DEFINED, time(), false ),
326 | array( -1, time(), false ),
327 | // defined password lifetime, never updated
328 | array( 15, 0, true ),
329 | // defined password lifetime, updated less than lifetime days ago
330 | array( 15, strtotime( 'now - 3 days' ), false ),
331 | // defined password lifetime, updated more than lifetime days ago
332 | array( 15, strtotime( 'now - 20 days' ), true ),
333 | );
334 | }
335 |
336 | /**
337 | * Helper method that creates a new user.
338 | * Currently only creates in users/guest_accounts.
339 | * First and last name will be a splitup of username
340 | *
341 | * @param string $username
342 | * @param string $password If not provided, uses the username as password
343 | * @param string $email If not provided, uses 'test.ez.no'
344 | *
345 | * @return eZContentObject
346 | */
347 | protected static function createUser( $username, $password = false, $email = false )
348 | {
349 | $firstname = substr( $username, 0, floor( strlen( $username ) / 2 ) );
350 | $lastname = substr( $username, ceil( strlen( $username ) / 2 ) );
351 |
352 | if ( $email === false )
353 | $email = "$username@test.ez.no";
354 | if ( $password === false )
355 | $password = $username;
356 |
357 | $user = new ezpObject( 'user', eZContentObjectTreeNode::fetchByPath( 'users/guest_accounts' ) );
358 | $user->first_name = $firstname;
359 | $user->last_name = $lastname;
360 | $user->user_account = $account = sprintf( '%s|%s|%s|%d',
361 | $username, $email,
362 | eZUser::createHash( $username, $password, eZUser::site(), eZUser::PASSWORD_HASH_MD5_USER ),
363 | eZUser::PASSWORD_HASH_MD5_USER );
364 | $user->publish();
365 | $user->refresh();
366 |
367 | return $user->object;
368 | }
369 |
370 | /**
371 | * PaEx creation time
372 | * @var int
373 | **/
374 | protected $paexTime;
375 |
376 | /**
377 | * PaEx test instance
378 | * @var eZPaEx
379 | **/
380 | protected $paex;
381 |
382 | /**
383 | * @var eZINI
384 | **/
385 | protected $paexINI;
386 | }
387 |
388 | ?>
--------------------------------------------------------------------------------
/datatypes/ezpaex/ezpaextype.php:
--------------------------------------------------------------------------------
1 | false,
26 | 'serialize_supported' => true ) );
27 | }
28 |
29 | /**
30 | * @deprecated Use ezpaextype::__construct() instead
31 | */
32 | public function ezpaextype()
33 | {
34 | self::__construct();
35 | }
36 |
37 | /**
38 | * Delete stored object attribute
39 | */
40 | function deleteStoredObjectAttribute( $contentObjectAttribute, $version = null )
41 | {
42 | $db = eZDB::instance();
43 | $paexID = $contentObjectAttribute->attribute( "contentobject_id" );
44 |
45 | $res = $db->arrayQuery( "SELECT COUNT(*) AS version_count FROM ezcontentobject_version WHERE contentobject_id = $paexID" );
46 | $versionCount = $res[0]['version_count'];
47 |
48 | if ( $version == null || $versionCount <= 1 )
49 | {
50 | eZPaEx::removePaex( $paexID );
51 | }
52 | }
53 |
54 | /**
55 | * Validates input on content object level
56 | *
57 | * @return eZInputValidator::STATE_ACCEPTED or eZInputValidator::STATE_INVALID if
58 | * the values are accepted or not
59 | */
60 | function validateObjectAttributeHTTPInput( $http, $base, $contentObjectAttribute )
61 | {
62 | $integerValidator = new eZIntegerValidator(0);
63 |
64 | $passwordlifetime = false;
65 | $expirationnotification = false;
66 | $updatechildren = false;
67 |
68 | if ( $http->hasPostVariable( $base . "_data_paex_passwordlifetime_" . $contentObjectAttribute->attribute( "id" ) ) )
69 | {
70 | $passwordlifetime = $http->postVariable( $base . "_data_paex_passwordlifetime_" . $contentObjectAttribute->attribute( "id" ) );
71 | }
72 | if ( $http->hasPostVariable( $base . "_data_paex_expirationnotification_" . $contentObjectAttribute->attribute( "id" ) ) )
73 | {
74 | $expirationnotification = $http->postVariable( $base . "_data_paex_expirationnotification_" . $contentObjectAttribute->attribute( "id" ) );
75 | }
76 |
77 | // Check if passwordlifetime is set, that it's an integer >= 0
78 | $statusPasswordlifetime = $integerValidator->validate( $passwordlifetime );
79 | if ( $statusPasswordlifetime != eZInputValidator::STATE_ACCEPTED && trim( $passwordlifetime ) )
80 | {
81 | $contentObjectAttribute->setValidationError( ezpI18n::tr( 'mbpaex/classes/datatypes',
82 | 'The password lifetime must be an integer >= 0' ) );
83 | return eZInputValidator::STATE_INVALID;
84 | }
85 |
86 | // Check if expirationnotification is set, that it's an integer >= 86400 (1 day)
87 | $integerValidator->setRange( 86400, false );
88 | $statusExpirationnotification = $integerValidator->validate( $expirationnotification );
89 | if ( $statusExpirationnotification != eZInputValidator::STATE_ACCEPTED && trim( $expirationnotification ) )
90 | {
91 | $contentObjectAttribute->setValidationError( ezpI18n::tr( 'mbpaex/classes/datatypes',
92 | 'The expiration notification time must be an integer >= 86400' ) );
93 | return eZInputValidator::STATE_INVALID;
94 | }
95 |
96 | // Check if password validates regexp
97 | $contentObjectID = $contentObjectAttribute->attribute( "contentobject_id" );
98 |
99 | // Check if paex object for the current coID exists, use default one if needed.
100 | $paex = $contentObjectAttribute->content();
101 | if ( $paex === null )
102 | {
103 | $paex = eZPaEx::create( $contentObjectID );
104 | }
105 |
106 | // If the current contentobject is a user, check if the password has changed and validate if needed
107 | if ( $paex->isUser() )
108 | {
109 | // Search for password entered in the form
110 | foreach ( $http->postVariable( $base . '_id' ) as $coaid )
111 | {
112 | if ($http->hasPostVariable($base . '_data_user_password_' . $coaid))
113 | {
114 | $newPassword = $http->postVariable($base . '_data_user_password_' . $coaid);
115 | break;
116 | }
117 | }
118 |
119 | if (trim($newPassword) && ($newPassword != "_ezpassword"))
120 | {
121 | if ( $paex->canEdit() )
122 | {
123 | if ($http->hasPostVariable( $base . "_data_paex_passwordvalidationregexp_" . $contentObjectAttribute->attribute( "id" ) ))
124 | {
125 | $paex->setAttribute('passwordvalidationregexp', $http->postVariable( $base . "_data_paex_passwordvalidationregexp_" . $contentObjectAttribute->attribute( "id" ) ));
126 | }
127 | }
128 | if (!$paex->validatePassword($newPassword))
129 | {
130 | $contentObjectAttribute->setValidationError( ezpI18n::tr( 'mbpaex/classes/datatypes',
131 | "The password doesn't match the validation rule.
132 | Previous password will be preserved if there is any." ) );
133 | return eZInputValidator::STATE_INVALID;
134 | }
135 | }
136 | }
137 | else // If we are updating a group, try to check the updatechildren checkbox
138 | {
139 | if ($http->hasPostVariable( $base . "_data_paex_updatechildren_" . $contentObjectAttribute->attribute( "id" ) ))
140 | {
141 | $updatechildren = $http->postVariable( $base . "_data_paex_updatechildren_" . $contentObjectAttribute->attribute( "id" ) );
142 | }
143 | // Check if updatechildren is set, that it's an integer 0 or 1 (1 day)
144 | $integerValidator->setRange(0, 1);
145 | $statusUpdatechildren = $integerValidator->validate($updatechildren);
146 | if ( $statusUpdatechildren != eZInputValidator::STATE_ACCEPTED && trim($updatechildren) )
147 | {
148 | $contentObjectAttribute->setValidationError( ezpI18n::tr( 'mbpaex/classes/datatypes',
149 | 'Wrong value in updatechildren field' ) );
150 | return eZInputValidator::STATE_INVALID;
151 | }
152 | }
153 | return eZInputValidator::STATE_ACCEPTED;
154 | }
155 |
156 | /**
157 | * Fetches all variables from the object
158 | *
159 | * @return bool true if fetching of class attributes are successfull, false if not
160 | */
161 | function fetchObjectAttributeHTTPInput( $http, $base, $contentObjectAttribute )
162 | {
163 | $contentObjectID = $contentObjectAttribute->attribute( "contentobject_id" );
164 |
165 | // check if paex object for the current coID exists, create if needed.
166 | $paex = $contentObjectAttribute->content();
167 | if ( $paex === null )
168 | {
169 | $paex = eZPaEx::create( $contentObjectID );
170 | }
171 |
172 | // Set current values as default ones
173 | $passwordvalidationregexp = $paex->attribute( 'passwordvalidationregexp' );
174 | $passwordlifetime = $paex->attribute( 'passwordlifetime' );
175 | $expirationnotification = $paex->attribute( 'expirationnotification' );
176 | $passwordLastUpdated = $paex->attribute( 'password_last_updated' );
177 | $updatechildren = $paex->attribute( 'updatechildren' );
178 | $expirationnotificationSent = $paex->attribute( 'expirationnotification_sent' );
179 |
180 | // Update current values with new ones entered in the form if there are any
181 | if ($http->hasPostVariable( $base . "_data_paex_passwordvalidationregexp_" . $contentObjectAttribute->attribute( "id" ) ) )
182 | {
183 | $passwordvalidationregexp = $http->postVariable( $base . "_data_paex_passwordvalidationregexp_" . $contentObjectAttribute->attribute( "id" ) );
184 | }
185 |
186 | if ($http->hasPostVariable( $base . "_data_paex_passwordlifetime_" . $contentObjectAttribute->attribute( "id" ) ) )
187 | {
188 | $passwordlifetime = $http->postVariable( $base . "_data_paex_passwordlifetime_" . $contentObjectAttribute->attribute( "id" ) );
189 | }
190 |
191 | if ($http->hasPostVariable( $base . "_data_paex_expirationnotification_" . $contentObjectAttribute->attribute( "id" ) ) )
192 | {
193 | $expirationnotification = $http->postVariable( $base . "_data_paex_expirationnotification_" . $contentObjectAttribute->attribute( "id" ) );
194 | }
195 | // Be sure passwordlifetime is set
196 | if ( trim( $passwordlifetime ) == '' )
197 | {
198 | $passwordlifetime = eZPaEx::NOT_DEFINED;
199 | }
200 |
201 | // Be sure expirationnotification is set
202 | if ( trim( $expirationnotification ) == '' )
203 | {
204 | $expirationnotification = eZPaEx::NOT_DEFINED;
205 | }
206 |
207 | // If we are editing a user account set it's password_last_updated as needed.
208 | if ( $paex->isUser() )
209 | {
210 | // Search for password entered in the form
211 | $newPassword = "";
212 | foreach ( $http->postVariable( $base . '_id' ) as $coaid )
213 | {
214 | if ( $http->hasPostVariable( $base . '_data_user_password_' . $coaid ) )
215 | {
216 | $newPassword = $http->postVariable( $base . '_data_user_password_' . $coaid );
217 | break;
218 | }
219 | }
220 | // Check if the password has changed
221 | if ( trim( $newPassword ) && ( $newPassword != "_ezpassword" ) )
222 | {
223 | $currentUserID = eZUser::currentUserID();
224 | if ( $currentUserID == $contentObjectID )
225 | {
226 | // If self editing, set last_updated to current time
227 | $passwordLastUpdated = time();
228 |
229 | // if audit is enabled password changes should be logged
230 | eZAudit::writeAudit( 'user-password-change-self', array( ) );
231 | }
232 | else if ( $currentUserID == eZUser::anonymousId() )
233 | {
234 | // register, @see http://issues.ez.no/15391
235 | $passwordLastUpdated = time();
236 | }
237 | else
238 | {
239 | // If changing other user's password, set last_updated to 0 to force
240 | // password change in the next connection
241 | $passwordLastUpdated = 0;
242 |
243 | // if audit is enabled password changes should be logged
244 | $targetUser = eZUser::fetch( $contentObjectID );
245 | eZAudit::writeAudit( 'user-password-change', array( 'User id' => $targetUser->attribute( 'contentobject_id' ), 'User login' => $targetUser->attribute( 'login' ) ) );
246 | }
247 | // Password has changed, reset expirationnotification_sent flag to send again a notification when this new password be about to expire
248 | $expirationnotificationSent = 0;
249 | }
250 | }
251 | else
252 | {
253 | // If we are updating a user group and don't have the updatechildren post var, set updatechildren flag to disabled
254 | if ($http->hasPostVariable( $base . "_data_paex_updatechildren_" . $contentObjectAttribute->attribute( "id" ) ))
255 | {
256 | $updatechildren = $http->postVariable( $base . "_data_paex_updatechildren_" . $contentObjectAttribute->attribute( "id" ) );
257 | }
258 | else
259 | {
260 | $updatechildren = 0;
261 | }
262 | }
263 |
264 | if ( $paex->canEdit() )
265 | {
266 | // If user has permission, update full paex object with possible new values
267 | $paex->setInformation( $contentObjectID, $passwordvalidationregexp, $passwordlifetime, $expirationnotification, $passwordLastUpdated, $updatechildren, $expirationnotificationSent );
268 | }
269 | else
270 | {
271 | // If user don't have permission to update paex data, only update the password_last_updated and expirationnotification_sent fields
272 | $paex->setAttribute( 'password_last_updated',$passwordLastUpdated );
273 | $paex->setAttribute( 'expirationnotification_sent',$expirationnotificationSent );
274 | }
275 |
276 | $contentObjectAttribute->setContent( $paex );
277 | return true;
278 | }
279 |
280 | /**
281 | * Store the content.
282 | */
283 | function storeObjectAttribute( $contentObjectAttribute )
284 | {
285 | $paex = $contentObjectAttribute->content();
286 | if ( !$paex instanceof eZPaEx )
287 | {
288 | // create a default paex object
289 | $paex = eZPaEx::create( $contentObjectAttribute->attribute( "contentobject_id" ) );
290 | }
291 | $paex->store();
292 | $contentObjectAttribute->setContent( $paex );
293 | }
294 |
295 | /**
296 | * Get empty paex data values from parent.
297 | *
298 | * @return bool True if the value was stored correctly.
299 | */
300 | function onPublish( $contentObjectAttribute, $contentObject, $publishedNodes )
301 | {
302 | eZDebug::writeDebug( 'Start', __METHOD__ );
303 | $paex = $contentObjectAttribute->content();
304 | if ( !$paex instanceof eZPaEx )
305 | {
306 | return true;
307 | }
308 |
309 | // Update empty paex data from parent paex
310 | // NOTE: if the current user don't have permission to edit paex data, and is
311 | // creating a new object (publishing version 1), force paex object update
312 | // to get values set in parent
313 | if ( !$paex->canEdit() && $contentObject->attribute( 'current_version' ) == 1 )
314 | $paex->updateFromParent( true );
315 | else
316 | $paex->updateFromParent();
317 |
318 | eZDebug::writeDebug( 'End', __METHOD__ );
319 | return true;
320 | }
321 |
322 | /**
323 | * @return bool true if the datatype finds any content in the attribute \a $contentObjectAttribute.
324 | */
325 | function hasObjectAttributeContent( $contentObjectAttribute )
326 | {
327 | $paex = $this->objectAttributeContent( $contentObjectAttribute );
328 | if ( is_object( $paex ) )
329 | return true;
330 | return false;
331 | }
332 |
333 | /**
334 | * Returns the content.
335 | */
336 | function objectAttributeContent( $contentObjectAttribute )
337 | {
338 | $paexID = $contentObjectAttribute->attribute( "contentobject_id" );
339 | $paex = eZPaEx::fetch( $paexID );
340 | return $paex;
341 | }
342 |
343 | /**
344 | * Returns the meta data used for storing search indeces.
345 | */
346 | function metaData( $contentObjectAttribute )
347 | {
348 | return $contentObjectAttribute->attribute('id');
349 | }
350 |
351 | /**
352 | * Returns the value as it will be shown if this attribute is used in the
353 | * object name pattern.
354 | */
355 | function title( $contentObjectAttribute, $name = null )
356 | {
357 | return $contentObjectAttribute->attribute('id');
358 | }
359 |
360 | /**
361 | * @return true if the datatype can be indexed
362 | */
363 | function isIndexable()
364 | {
365 | return true;
366 | }
367 | }
368 |
369 | eZDataType::register( ezpaextype::DATA_TYPE_STRING, "ezpaextype" );
370 | ?>
371 |
--------------------------------------------------------------------------------