How to set up smartphones and PCs. Informational portal
  • home
  • Errors
  • Building a simple contact form with Angularjs and php. User data security Why was this form installed?

Building a simple contact form with Angularjs and php. User data security Why was this form installed?

It is very convenient to always know what specific version this or that assembly of the project is. This is usually done by entering a version number consisting of several digits. I am a proponent of a 4-digit structure like:

Together, this forms the full version naming (Major.Minor.Pathch.Build):

Some people use a unique numeric value as build, which is incremented every time, for example, during a night build. I believe that there is no point in this - it is much more convenient to bind this number to a revision in the repository. I use Subversion and CMake, so I will demonstrate how you can automate the posting of a build version with these tools.

First, you need to add a header file to the project (for example, version.h):

#include #include namespace Version (const std :: string & AsText (); boost :: uint64_t AsNumber ();)

Here is a simple interface through which you can get the full version number from the program in text form or as a unique integer identifier.

Now I will give the content of version.cpp:

#include #include "../version.h" namespace (const boost :: uint8_t MAJOR = 4; const boost :: uint16_t MINOR = 6; const boost :: uint16_t PATCH = 12; const boost :: uint32_t BUILD = 589; // This value will be changed automatically) const std :: string & Version :: AsText () (static const std :: string text = boost :: str (boost :: format ("% 1%.% 2%.% 3%.% 4%") % static_cast< unsigned >(MAJOR)% MINOR% PATCH% BUILD); return text; ) boost :: uint64_t Version :: AsNumber () (BOOST_STATIC_ASSERT (BUILD< 0xFFFFFF ) ; using namespace boost; const size_t size = sizeof (uint64_t ) ; static const boost:: uint64_t number = (static_cast < uint64_t >(MAJOR)<< (size - sizeof (MAJOR) ) * 8 ) | (static_cast < uint64_t >(MINOR)<< (size - sizeof (MAJOR) - sizeof (MINOR) ) * 8 ) | (static_cast < uint64_t >(PATCH)<< (size - sizeof (MAJOR) - sizeof (MINOR) - sizeof (PATCH) ) * 8 ) | BUILD; return number; }

Everything is trivial here and, I think, does not require comments. The last thing left is the mechanism for changing the BUILD value to the revision number in the repository. CMake will handle this just fine, just add the following code to CMakeLists.txt:

set (VERSION_FILE ../ common / sources / version.cpp) find_package (Subversion REQUIRED) Subversion_WC_INFO ($ (PROJECT_SOURCE_DIR) Repo) file (READ $ (VERSION_FILE) OLD_CODE) foreach (LINE $ (OLD_CODEX)) "string = (+) "BUILD_NUMBER $ (LINE)) if (BUILD_NUMBER) string (REGEX REPLACE" + $ "$ (Repo_WC_REVISION) LINE $ (LINE)) endif () set (NEW_CODE $ (NEW_CODE) $ (LINE)) endforeach ( LINE) file (WRITE $ (VERSION_FILE) " $ (NEW_CODE) ")

The only subtlety in the script is in the last line, and more specifically, the quotes in "$ (NEW_CODE)", without them all “;” will be removed.

We need the following pages:

  • Registration page with registration form
  • Account activation page
  • Password recovery page
  • Password reset page

The site login form will be placed on all pages of the site (for example, in the header).

This is the registration page we want to receive:

Here, the account type will determine which group we register the user with. Also, the field for identification (username) will be email.

Add a snippet call to the page Register:

[[! Register? & submitVar = `register-btn` & activationResourceId =` 27` & activationEmailTpl = `Email.Activation` & activationEmailSubject =` You are registered on example.com` & placeholderPrefix = `reg.` & successMsg =`

Thank you for registering. To your email [[! + reg.email]] an email has been sent with a link to activate your account. Follow this link to complete your registration.
`& usernameField =` email` & usergroupsField = `reg_type` & customValidators =` valueIn` & validate = `username: blank, reg_type: valueIn = ^ Readers; Writers; Idlers ^, fullname: required: minLength = ^ 6 ^, password: required: minLength = ^ 6 ^, password_confirm: password_confirm = ^ password ^, email: required: email`]] [[! + Error.message: default = `[[! $ Register.Form]]`]]

Please note that all registration tags need necessarily call uncached. The same rules apply when processing forms with the FormIt snippet.

Let's analyze the call parameters:

& submitVar = `register-btn`- specifies the name attribute of the tag input... That is, the snippet will only work if the form is submitted by a button with a specific name.

& activationResourceId = `42`- looking ahead, 42 is the identifier of the page on which we will activate the user.

& activationEmailTpl = `Email.Activation`- chunk with an activation letter, about it later.

& placeholderPrefix = `reg.`- indicates that all placeholders, with rare exceptions (more on that later), which are created in this snippet, must begin with "reg."

& successMsg- the message that will be displayed upon successful form submission. Note that you can specify values ​​from the form and any other tags in it. This message will be written to the placeholder [[! + error.message]]. Quite a strange name, and there is an error in the documentation at the moment. It is written there [[! + reg.error.message]], but it follows from the component code that this is not the case.

& usernameField = `email`- indicates that the email field will be used as the username.

& usergroupsField = `reg_type`- defines the field that sets the group to which the new user will be added.

& customValidators = `valueIn`- indicates additional validators to be created manually.

& validate- validators are set separated by commas for each field, and if several validators are required for one field, then they are also separated by a colon. Let's analyze them separately:

username: blank Is a simple spam trap, which means that the username field should be left blank.

reg_type: valueIn = ^ Readers; Writers; Idlers ^- we limit the possible groups to the three indicated. In the initial delivery, this is not the case, and evil hackers can register, for example, under the Administrator group (if you have not renamed it).

fullname: required: minLength = ^ 6 ^- the fullname field must not be empty and contain at least 6 characters.

password: required: minLength = ^ 6 ^- similarly for the password.

password_confirm: password_confirm = ^ password ^- passwords must match.

email: required: email- e-mail should not be empty and be the mail itself.

Design [[! + error.message: default = `[[! $ Register.Form]]`]] displays a message about successful form submission or form chunk if you just visited the page or filled it out incorrectly.

Let's create the above validator valueIn... To do this, create a snippet with the name valueIn and the following code:

$ valueIn = explode (";", $ param); return in_array ($ value, $ valueIn);

Now you need to create a chunk Register.Form ... In this case, it will be as follows (using Bootstrap 3):

[[! + reg.error.fullname: notempty = `
[[! + reg.error.fullname]]
`]]
[[! + reg.error.email: notempty = `
[[! + reg.error.email]]
`]]
[[! + reg.error.password: notempty = `
[[! + reg.error.password]]
`]]
[[! + reg.error.password_confirm: notempty = `
[[! + reg.error.password_confirm]]
`]]

All fields are required

In this form, I will note a few things about MODX:


- the form is processed on the same page on which it is displayed.

Setting the value from those received from the form so that in case of failure the user does not have to enter everything again.

[[! + reg.error.email: notempty = `[[! + reg.error.email]]`]]- again, in case of failure, an error message will be displayed below the field.

- be sure to indicate the name of the button if you previously set the property & submitVar.


Now it remains to create a chunk Email.Activation with the letter that the site sends to the user:

Thank you for registering! To activate your account, please follow the following link:

Activate your account on Example.Com

After activation, you will be able to log in by entering your email and password:

Login:[[+ email]]

Password:[[+ password]]


Here you can use placeholders with the names of the form fields. Note that they are already written without "reg." A placeholder is also added [[+ confirmUrl]], in which the activation link has already been generated, you don't even need to do anything.


The final touch to the art of registering a new account using a component Login will create an activation page. We use an empty template for this page, and in the content of the page, we just need to specify a call to the tag:

[[! ConfirmRegister? & redirectTo = `1`]]

where 1 is the identifier of the page to which the user will be redirected in case of successful activation. In this case, he will already be logged in.


Let's start configuring the login to the user profile. The authorization form will be simple:

Let's add it by calling it in the right place:

[[! Login? & loginTpl = `Auth.Login` & logoutTpl =` Auth.Logout` & errTpl = `Auth.Login.Error` & actionKey =` action` & loginKey = `login` & redirectToPrior =` 1` & logoutResourceId = `1`]]

Here we specify a chunk with the login form shown above ( & loginTpl = `Auth.Login`), a chunk with a code shown to authorized users ( & logoutTpl = `Auth.Logout`), a small chunk with the output of a login error ( & errTpl = `Auth.Login.Error`). The parameters follow:

& actionKey = `action` and & loginKey = `login`- the main identifiers for processing the request. The first means the name of the parameter in the POST request, and the second means its value. That is, the form must pass the value $ _POST ["action"] = "login" so that the snippet Login processed it.

& redirectToPrior = `1`- means that after logging in, we will be redirected to the same page from which we logged in.

& logoutResourceId = `1`- when leaving the profile, we will go to the page with the identifier 1.


Chunk Auth.Login :

[[! + errors]]

The form is processed on the same page. If an error occurs, it will be displayed below the form in the placeholder [[! + errors]]. You also need to remember the links to resources with Registration and password recovery. Note that in the field for e-mail name = "username" - it was in this field that the snippet duplicated the mail Register and it is unique to users.


Chunk Auth.Logout:

[] `& tpl =` User.HeaderBadge` & innerJoin = `(" modUserGroupMember ":(" alias ":" modUserGroupMember "," on ":" modUser.id = modUserGroupMember.member ")," modUserGroup ":(" alias " : "modUserGroup", "on": "modUserGroupMember.user_group = modUserGroup.id")) `& select =` ("modUserGroup" :( "group_name": "modUserGroup.name")) `]]

Log out of profile

This part is optional if all users are in the same group. But to display a user group, the standard snippets included in the Login component are not enough. You can write a simple snippet to get the group name on xPDO, or you can use a ready-made snippet pdoUsers included in the package pdoTools... Parameters specified in this snippet:

& users = `[[+ modx.user.id]]`- we select only the current authorized user.

& tpl = `User.HeaderBadge`- a chunk in which we will display brief information about the user.

& innerJoin- JSON with joins of user group tables, description is beyond the scope of this article. The main thing is it works J.

& select- JSON adding the modUserGroup.name field with the group_name alias to the selection.


Chunk with the user's badge User.HeaderBadge :

You are logged in as [[+ group_name]][[+ fullname]] Personal account

If we didn't need a user group, then the contents of this chunk could be inserted directly into the chunk Auth.Logout ... Here you can display placeholders with any modUser and modUserProfile fields plus using pdoUsers added a field group_name.


In a chunk Auth.Login.Error simple error output:

[[+ msg]]

We are done with the login. At this point, the user can register and login successfully. But what if he forgot his password? In this case, he clicks on the link "Forgot your password?" and goes to the password recovery page, which we pre-create and place the call there:

[[! ForgotPassword? & tpl = `Auth.ForgotPass.Form` & submitVar =` forgotpass` & errTpl = `Auth.Login.Error` & sentTpl =` Auth.ForgotPass.Sent` & emailTpl = `Email.ForgotPass` & emailSubject =` Restoring account access on Example. Com` & resetResourceId = `29`]]

Let's analyze the parameters of this call:

& tpl = `Auth.ForgotPass.Form`- chunk of the form in which the user enters his email.

& submitVar = `forgotpass`- in the case of the ForgotPassword snippet, it is enough for the parameter with this name to be passed to the server, no matter with which non-empty value.

& errTpl = `Auth.Login.Error`- error output is similar to Login snippet

& sentTpl = `Auth.ForgotPass.Sent`- this chunk contains content that will be displayed in case of successful sending of a letter to change the password.

& emailTpl = `Email.ForgotPass`- the letter itself is contained here.

& emailSubject= `Restoring access to an account on the Example.Com site` - message header.

& resetResourceId = `29`- resource identifier on which the password will be reset to a new one.


Chunk Auth.ForgotPass.Form:

[[+ loginfp.errors]]

What's new here is just another way of displaying errors in the placeholder [[+ loginfp.errors]] and passing a parameter that it is this form that resets the password: .

Auth.ForgotPass.Sent:

Account recovery information has been sent to the specified email address: [[+ email]].

Here you can use the data from the form above.


Email.ForgotPass:

[[+ fullname]],

To activate your new password, please visit the following link:

I want a new password

If everything went well, you will be able to log into your profile with the following information:

Login:[[+ username]]

Password:[[+ password]]

Thank you,
Site Administration Example.Com

Everything is very similar to the chunk of the activation letter, only the password is generated here in the snippet.


The final touch remains to create a resource to which the user will go from the letter to update the password. In this resource, we need a call:

[[! ResetPassword: empty = `

You have not ordered a password reset. Perhaps you have the wrong address. You can go to the main page of the site or use the menu above.

`? & tpl = `Auth.ForgotPass.Reset`]]

This code will display a message if suddenly someone wanders into this page again or just by accident. And if the password is successfully reset, a message from the chunk will be displayed Auth.ForgotPass.Reset:

Your password has been successfully reset to the one specified in the letter. You can now log in with this password. Do not forget to change it in your profile.

Now we have a fully working system of authorization and registration of users. Changing the profile of authorized users will be left outside the scope of the article.


1. Create a registration page and add a snippet call to it Register.

2. Create chunks with a registration form Register.Form and activation letter Email.Activation.

3. Create a registration confirmation page and place a snippet call on it ConfirmRegister.

4. Add a snippet call Login where we want to place the login form and the badge of the authorized user.

5. Create a chunk with a login form Auth.Login , chunk with information about the authorized user Auth.Logout , chunk with error message Auth.Login.Error .

6. Create a password recovery page and place a snippet call on it ForgotPassword.

7. Create a chunk Auth.ForgotPass.Form with a password recovery form, chunk Auth.ForgotPass.Sent with a message about the successful sending of the letter, chunk Email.ForgotPass with a letter to reset the password.

8. Create a resource with a final password reset and place a snippet call in it ResetPassword.

9. Create a chunk Auth.ForgotPass.Reset with a message about successful password reset.

That's all. I will be glad to any additions and comments.

Foolproof is a set of measures to prevent the entry of incorrect information into a form. For example, if you need to enter a positive number from 0 to 10 in a field, then you should check that the user does not enter text or a number that does not lie in the specified range, i.e. the number must not be less than zero or more than ten.

Why is incorrect information being entered? This is mainly due to three reasons.

  1. The user made a mistake by accident, for example, inattentively read what he needs to indicate.
  2. On a web page, they are ambiguously asked to enter data, so the user has to guess and make an assumption about what they really want from him. In this case, the views of the developer and the user do not always coincide.
  3. There are a number of people who take instructions as a challenge and try to do the opposite. Such users reason like this: “Yeah, I'm asked to enter a number. What happens if I indicate the letters? " After that, they ask obviously incorrect information and see what it will lead to.

It should be understood that precise and correct formulations, although they reduce the likelihood of errors, in no way save you from them. Only technical means on the server side allow you to get the desired result and avoid entering incorrect information. Nevertheless, revision or, as it is also called, client-side validation allows you to quickly check the data entered by the user for correctness, without submitting the form to the server. This saves the user time and reduces the load on the server. From the point of view of usability, there are also pluses - the user immediately receives a message about what information he indicated incorrectly and can correct his mistake.

Obligatory field

Some form fields must be filled in before sending them to the server. This, for example, applies to the registration form, where you are required to enter a username and password. The required attribute is used to specify required fields, as shown in Example 1.

Example 1. The required attribute

HTML5 IE 10+ Cr Op Sa Fx

Obligatory field

Login:

Password:

Required fields must be filled in before submitting the form, otherwise the form will not be sent to the server and the browser will issue a warning about this. The type of message depends on the browser; for example, Chrome displays a tooltip, as shown in Fig. one.

Rice. 1. Required field is not filled

Correctness of data

Initially, there are two fields in which the data entered by the user is checked automatically. This is the web address and email address. The Chrome browser also checks the calendar data field for validity, but only because it does not have a click-to-select calendar interface. These elements are characterized by the following rules.

  • Web address ( ) must contain the protocol (http: //, https: //, ftp: //).
  • E-mail address ( ) must contain letters or numbers before the @ symbol, after it, then a period and first-level domain.

Browsers have slightly different policies for validating user data. For example, Opera automatically substitutes the http: // protocol in front of the entered text, while other browsers expect it from the user. Chrome and Opera require a dot to be in the mailing address, it is optional for Firefox.

Example 2 shows a form with required fields in which two fields are validated by the browser.

Example 2. Correctness of data

HTML5 IE 10+ Cr Op Sa Fx

Correctness of data

Fill out the form (all fields are required)

Name:

Email:

Site:

Opera only validates a form element if the name attribute is present.

What happens in Opera when you enter incorrect data is shown in Fig. 2.

Rice. 2. Warning about incorrect data

Input Template

Some data cannot be categorized as one type of form element, so you have to use a text box for it. Moreover, their input takes place according to a certain standard. So, the IP address contains four numbers separated by a dot (192.168.0.1), the postal code of Russia is limited to six digits (124007), the phone contains a city code and a specific number of digits often separated by a hyphen (391 555-341-42), etc. The browser needs specify an input template so that it validates user input according to it. For this, the pattern attribute is used, and its value is a regular expression. Some typical values ​​are listed in table. one.

Example 3 asks for a hexadecimal color value (# ffcc00) and if it is not in this range, the browser displays an error message.

Example 3. Input Template

HTML5 IE 10+ Cr Op Sa Fx

Color input

Enter a hexadecimal color value (must start with #)

In fig. 3 shows a warning in the Chrome browser.

Rice. 3. The entered data does not match the template

Cancellation of validation

Validation is not always required for a form, for example, a developer wants to use a universal solution in JavaScript and he doesn't need duplicate validation by the browser. In such cases, you need to disable inline validation. For this, the novalidate attribute of the tag is applied.

... Example 4 shows the use of this attribute.

Example 4. Cancellation of validation

HTML5 IE 10+ Cr Op Sa Fx

Novalidate attribute

For a similar purpose, the formnovalidate attribute is used, which is added to the button for submitting the form, in this case to the tag ... In this case, the form from example 4 will look like this.

For any web developer, there is no more serious problem yet than the complete cross-browser compatibility of his product. Probably, this is one of the main tasks of a good specialist: to ensure that his site is always displayed correctly in all browsers.

Parameter required which is sometimes used for input does not work in ancient IE, which simply cannot be left that way. Retired users who still use IE6 should be just as easy on your site as users of the latest version of Google Chrome. Who other than web developers can take care of them.

About painful, about Internet Explorer

For normal browsers like Firefox, Opera and Google Chrome, this task is relatively easy. Even older versions of these browsers render html-code equally well, unless of course some new technology is used in it. But to achieve this in browsers of the Internet Explorer family, it takes a huge effort.

Each version of the Internet Exlorer browser has its own unique stupidity. What works in IE6 may not work properly in IE7, and vice versa. This zoo of Microsoft has not been able to overcome even in the latest version of its browser.

I can't understand why browser developers can't just open up and read the W3C standards for site building.

Therefore, as a web developer, I have to act as a kind of "layer" between capricious browsers and site visitors requiring knowledge and spectacles. And it's great that web-developers have succeeded so far.

So how do you get required to work in older versions of IE?

JS comes to our rescue. Previously, I could not stand it, but now I do not see a further way without it in the vastness of the "correct" WEB.

I did not invent the solution below myself, but took it from a bourgeois blog. Since I am greedy, and the blog is bourgeois, I will not link to it.

The function will be responsible for everything. fnCheckFields ()... Place the JS code on your website:

It is usually recommended to place it between html tags HEAD at the beginning of the page, but I would still recommend placing it at the very bottom of the page before the closing tag BODY... Thus, JS has less impact on page load speed.

The input window, where the required parameter must be entered, should look like this in html language:

This script works very simply: after clicking the button send, the script checks all inputs for the presence of the required parameter and if it finds it, then it looks at the entered value of this field accordingly. If nothing is entered into such an input, then a warning window about the need for input is displayed. Accordingly, the data is not sent anywhere.

It is also remarkable that if you have a normal browser that has already learned to understand this parameter as expected, such a warning window will not pop up and the standard tools for processing the required parameter for your browser will work.

Share on social media networks

Top related articles