Logo

Login Dialog Using and XML File

 

Introduction

The credentials used to authenticate users who need access to a file, a database or an application are usually stored in a list. These credentials are usually a combination of a username and a password. Just like any traditional file, an XML file can be used to store the login credentials. Normally, the XML part is only as flexible as a normal list can be. The advantage that an XML file may offer over a text or binary file is that XML provides a fairly easy way to navigate the list looking for a username or a combination of a username and a password.

Using an XML File

To store credentials in an XML file, your first decision may have to do with the structure of the file. You can store the credentials in separate tags of an parent element. For example, you can create an element that would be used for each combination of a username and a password. Here is an example:

<?xml version="1.0" encoding="utf-8">
<logininfo>
    <crendential>
        <username>johnsd</username>
        <password>73DD234j5h</password>
    <crendential>
    <crendential>
        <username>walterg</username>
        <password>2$34Hf37</password>
    <crendential>
</logininfo>

Another solution, which we will use here because it is a little easier (in our opinion of course) consists of creating the credentials as attributes of a tag. This appears to make it easy during validation since each element is considered at a time. Once an element is reached, we can consider its the attributes of its tag as a unit and check the combination.

 

Practical Learning: Login Authentication With XML

  1. If you want to follow, create a Windows Forms Application named Authenticator
  2. To add another form, on the main menu, click Project -> Add New Item...
  3. In the Templates section, click Windows Form
  4. In the Name box, type MainForm and press Enter
  5. Add a new XML file named credentials.xml and fill it as follows:
     
    <?xml version="1.0" encoding="utf-8"?>
    <logininfo>
      <credential username="pickettw" password="Patrice" />
      <credential username="reddingo" password="Collage" />
      <credential username="carterc" password="drapery" />
      <credential username="brownj" password="musical" />
    </logininfo>
  6. Display the first form and design the form as follows:
     
    Control Name Text Additional Properties
    Label   Username:  
    TextBox txtUsername    
    Label   Password:  
    TextBox txtPassword   PasswordChar: *
    Button btnOK OK  
    Button btnClose Cancel  
    Button btnNewAccount Create New Account  
    Form   Login Authentication FormBorderStyle: FixedDialog
    MinimizeBox: False
    MaximizeBox: False
    ShowInTaskbar: False
    StartPosition: CenterScreen
    AcceptButton: btnOK
    CancelButton: btnClose
  7. Add another form and set its name to NewAccount
  8. Design the form as follows:
     
    Control Name Text Additional Properties
    Label   Username:  
    TextBox txtUsername    
    Label   Password:  
    TextBox txtPassword   PasswordChar: *
    Label   Confirm Password:  
    TextBox txtConfirmPassword   PasswordChar: *
    Button btnOK OK  
    Button btnClose Cancel  
    Form   New Account Creation FormBorderStyle: FixedDialog
    MinimizeBox: False
    MaximizeBox: False
    ShowInTaskbar: False
    StartPosition: CenterParent
  9. Double-click the Cancel button and implement its event as follows:
     
    private: System::Void btnClose_Click(System::Object *  sender, System::EventArgs *  e)
    	{
    		 Close();
    	 }
  10. Scroll to the top of the file and declare two public String pointers named Username and Password:
     
    public __gc class NewAccount : public System::Windows::Forms::Form
    	{
    	public: 
    		NewAccount(void)
    		{
    			InitializeComponent();
    		}
    
    		String *Username;
    		String *Password;
            
  11. Double-click the OK button and implement its event as follows:
     
    private: System::Void btnOK_Click(System::Object *  sender, System::EventArgs *  e)
    	 {
    		 Username = this->txtUsername->Text;
    		 Password = this->txtPassword->Text;
    		 String *ConfPass = this->txtConfirmPassword->Text;
    
    		 if( Username->Equals(S"") == true )
    		 {
     MessageBox::Show(S"Invalid Username: We don't accept an empty username!");
    			 this->txtUsername->Focus();
    			 return;
    		 }
    		 if( Password->Equals(S"") == true )
    		 {
     MessageBox::Show(S"Invalid Password: We don't accept a blank password!");
    			 this->txtPassword->Focus();
    			 return;
    		 }
    		 if( String::Compare(Password, ConfPass) != 0 )
    		 {
    	 MessageBox::Show(S"The passwords you provided are not the same!");
    			 this->txtPassword->Focus();
    			 return;
    		 }
    
    		 this->DialogResult = DialogResult::OK;
    		 Close();
    	}
  12. Display the first form
  13. Double-click the Create New Account button
  14. Return to the form and double-click the OK button
  15. Return to the form and double-click the Cancel button
  16. Implement the events as follows:
     
    #pragma once
    
    #include "NewAccount.h"
    #include "MainForm.h"
    
    namespace Authenticator
    {
    	using namespace System;
    	using namespace System::ComponentModel;
    	using namespace System::Collections;
    	using namespace System::Windows::Forms;
    	using namespace System::Data;
    	using namespace System::Drawing;
    	using namespace System::Xml;
    
    	/// <summary> 
    	/// Summary for Form1
    	///
    	/// WARNING: If you change the name of this class, you will need to change the 
    	///          'Resource File Name' property for the managed resource compiler tool 
    	///          associated with all .resx files this class depends on.  Otherwise,
    	///          the designers will not be able to interact properly with localized
    	///          resources associated with this form.
    	/// </summary>
    	public __gc class Form1 : public System::Windows::Forms::Form
    	{	
    	public:
    		Form1(void)
    		{
    			InitializeComponent();
    		}
      
    	protected:
    		void Dispose(Boolean disposing)
    		{
    			if (disposing && components)
    			{
    				components->Dispose();
    			}
    			__super::Dispose(disposing);
    		}
    
    
    	private: System::Windows::Forms::Button *  btnClose;
    	private: System::Windows::Forms::Button *  btnNewAccount;
    	private: System::Windows::Forms::TextBox *  txtPassword;
    	private: System::Windows::Forms::TextBox *  txtUsername;
    	private: System::Windows::Forms::Label *  label2;
    	private: System::Windows::Forms::Label *  label1;
    	private: System::Windows::Forms::Button *  btnOK;
    
    	private:
    		/// <summary>
    		/// Required designer variable.
    		/// </summary>
    		System::ComponentModel::Container * components;
    
    		/// <summary>
    		/// Required method for Designer support - do not modify
    		/// the contents of this method with the code editor.
    		/// </summary>
    		void InitializeComponent(void)
    		{
    			this->btnOK = new System::Windows::Forms::Button();
    			this->btnClose = new System::Windows::Forms::Button();
    			this->btnNewAccount = new System::Windows::Forms::Button();
    			this->txtPassword = new System::Windows::Forms::TextBox();
    			this->txtUsername = new System::Windows::Forms::TextBox();
    			this->label2 = new System::Windows::Forms::Label();
    			this->label1 = new System::Windows::Forms::Label();
    			this->SuspendLayout();
    			// 
    			// btnOK
    			// 
    			this->btnOK->Location = System::Drawing::Point(16, 80);
    			this->btnOK->Name = S"btnOK";
    			this->btnOK->TabIndex = 39;
    			this->btnOK->Text = S"OK";
    			this->btnOK->Click += new System::EventHandler(this, btnOK_Click);
    			// 
    			// btnClose
    			// 
    			this->btnClose->DialogResult = System::Windows::Forms::DialogResult::Cancel;
    			this->btnClose->Location = System::Drawing::Point(104, 80);
    			this->btnClose->Name = S"btnClose";
    			this->btnClose->Size = System::Drawing::Size(88, 23);
    			this->btnClose->TabIndex = 37;
    			this->btnClose->Text = S"Cancel";
    			this->btnClose->Click += new System::EventHandler(this, btnClose_Click);
    			// 
    			// btnNewAccount
    			// 
    			this->btnNewAccount->Location = System::Drawing::Point(216, 16);
    			this->btnNewAccount->Name = S"btnNewAccount";
    			this->btnNewAccount->Size = System::Drawing::Size(88, 88);
    			this->btnNewAccount->TabIndex = 36;
    			this->btnNewAccount->Text = S"Create New Account";
    			this->btnNewAccount->Click += new System::EventHandler(this, btnNewAccount_Click);
    			// 
    			// txtPassword
    			// 
    			this->txtPassword->Location = System::Drawing::Point(96, 48);
    			this->txtPassword->Name = S"txtPassword";
    			this->txtPassword->PasswordChar = '*';
    			this->txtPassword->TabIndex = 35;
    			this->txtPassword->Text = S"";
    			// 
    			// txtUsername
    			// 
    			this->txtUsername->Location = System::Drawing::Point(96, 16);
    			this->txtUsername->Name = S"txtUsername";
    			this->txtUsername->TabIndex = 34;
    			this->txtUsername->Text = S"";
    			// 
    			// label2
    			// 
    			this->label2->Location = System::Drawing::Point(16, 48);
    			this->label2->Name = S"label2";
    			this->label2->Size = System::Drawing::Size(72, 16);
    			this->label2->TabIndex = 33;
    			this->label2->Text = S"Password:";
    			// 
    			// label1
    			// 
    			this->label1->Location = System::Drawing::Point(16, 16);
    			this->label1->Name = S"label1";
    			this->label1->Size = System::Drawing::Size(72, 16);
    			this->label1->TabIndex = 32;
    			this->label1->Text = S"Username:";
    			// 
    			// Form1
    			// 
    			this->AcceptButton = this->btnOK;
    			this->AutoScaleBaseSize = System::Drawing::Size(5, 13);
    			this->CancelButton = this->btnClose;
    			this->ClientSize = System::Drawing::Size(320, 118);
    			this->Controls->Add(this->btnOK);
    			this->Controls->Add(this->btnClose);
    			this->Controls->Add(this->btnNewAccount);
    			this->Controls->Add(this->txtPassword);
    			this->Controls->Add(this->txtUsername);
    			this->Controls->Add(this->label2);
    			this->Controls->Add(this->label1);
    			this->FormBorderStyle = System::Windows::Forms::FormBorderStyle::FixedDialog;
    			this->MaximizeBox = false;
    			this->MinimizeBox = false;
    			this->Name = S"Form1";
    			this->ShowInTaskbar = false;
    			this->StartPosition = System::Windows::Forms::FormStartPosition::CenterScreen;
    			this->Text = S"Login Authentication";
    			this->ResumeLayout(false);
    
    		}	
    	private: System::Void btnNewAccount_Click(System::Object *  sender, System::EventArgs *  e)
    			 {
    			 NewAccount *Acnt = new NewAccount;
    			 String *Username = 0, *Password = 0;
    			 String *ExistingUsername;
    			 bool UniqueUsername = true;
    
    			 if( Acnt->ShowDialog() == DialogResult::OK )
    			 {
    				 Username = Acnt->Username;
    				 Password = Acnt->Password;
    				 
    				 XmlTextReader *xtr = new XmlTextReader(S"credentials.xml");
    
    				 while(xtr->Read() )
    				 {
    					 switch(xtr->NodeType)
    					 {
    					 case XmlNodeType::Element:
    						 ExistingUsername = xtr->GetAttribute(S"username");
    
    						 if( Username->Equals(ExistingUsername) )
    							 UniqueUsername = false;
    
    						 break;
    					 }
    				 }
    			
    				 xtr->Close();
    				 
    				 if( UniqueUsername == true )
    				 {
    					 // Declare an XmlDocument that will be used to add a new item
    					 XmlDocument* XmlDoc = new XmlDocument();
    
    					 try {
    						 // Get the XML file and load it in the XmlDocument variable
    						 XmlDoc->Load(S"credentials.xml");
    
    						 // Create the new element
    						 XmlElement *Elm = XmlDoc->CreateElement(S"credential");
    						 // Create its attributes
    						 Elm->SetAttribute(S"username", Username);
    						 Elm->SetAttribute(S"password", Password);
    		
    						 // Add the new element to the file...
    						 XmlDoc->DocumentElement->AppendChild(Elm);
    						 // ... and save the document
    						 XmlDoc->Save(S"credentials.xml");
    
    						 MessageBox::Show(S"The account has been created!"
    								 S"\nYou can use your new account to login!");
    					 }
    					 catch (Exception *e)
    					 {
    						 MessageBox::Show(e->Message);
    					 }
    				 }
    				 else
    					 MessageBox::Show(S"The username you provided is already being used!!!");
    			 }
    			 }
    
    private: System::Void btnOK_Click(System::Object *  sender, System::EventArgs *  e)
    		 {
    			 String *strUsername = this->txtUsername->Text;
    			 String *strPassword = this->txtPassword->Text;
    			 String *Username, *Password;
    
    			 bool GoodLogin = false;
    
    			 if( strUsername->Equals(S"") )
    			 {
    				 MessageBox::Show(S"Invalid or empty username."
    								  S"\nPlease provide a username");
    				 this->txtUsername->Focus();
    				 return;
    			 }
    			 if( strPassword->Equals(S"") )
    			 {
    				 MessageBox::Show(S"Invalid or empty password."
    								  S"\nPlease type a valid password");
    				 this->txtPassword->Focus();
    				 return;
    			 }
    
    			 XmlTextReader *xtr = new XmlTextReader(S"credentials.xml");
    
    			 while(xtr->Read() )
    			 {
    				 switch(xtr->NodeType)
    				 {
    				 case XmlNodeType::Element:
    					 Username = xtr->GetAttribute(S"username");
    					 Password = xtr->GetAttribute(S"password");
    
    					 if( strUsername->Equals(Username) )
    					 {
    						 if( strPassword->Equals(Password) )
    							 GoodLogin = true;
    						 else
    							 GoodLogin = false;
    					 }
    					 break;
    				 }
    			 }
    			
    			 if( GoodLogin == true )
    			 {
    				 MainForm *FM = new MainForm;
    				 this->Hide();
    				 FM->ShowDialog();
    
    				 Close();
    			 }
    			 else
    				 MessageBox::Show(S"Invalid Credentials");
    		 }
    
    private: System::Void btnClose_Click(System::Object *  sender, System::EventArgs *  e)
    		 {
    			 Close();
    		 }
    };
    }
  17. Test the application
     

Home Copyright © 2004-2010 FunctionX, Inc.