Rahul23232 commited on
Commit
720df53
·
verified ·
1 Parent(s): 97cca92

Upload 7 files

Browse files
Files changed (6) hide show
  1. Dockerfile +13 -0
  2. LICENSE +21 -0
  3. README.md +382 -4
  4. app.py +112 -0
  5. requirements.txt +4 -0
  6. users.db +0 -0
Dockerfile ADDED
@@ -0,0 +1,13 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ FROM python:3.9
2
+
3
+ RUN useradd -m -u 1000 user
4
+ USER user
5
+ ENV PATH="/home/user/.local/bin:$PATH"
6
+
7
+ WORKDIR /app
8
+
9
+ COPY --chown=user ./requirements.txt requirements.txt
10
+ RUN pip install --no-cache-dir --upgrade -r requirements.txt
11
+
12
+ COPY --chown=user . /app
13
+ CMD ["gunicorn", "app:app", "-b", "0.0.0.0:7860"]
LICENSE ADDED
@@ -0,0 +1,21 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Rahul Bhaskar
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
README.md CHANGED
@@ -1,10 +1,388 @@
1
  ---
2
- title: Flaskloginsignupwebsite
3
  emoji: 💻
4
- colorFrom: red
5
- colorTo: pink
6
  sdk: docker
7
- pinned: false
 
 
8
  ---
9
 
10
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
  ---
2
+ title: Flask Login
3
  emoji: 💻
4
+ colorFrom: green
5
+ colorTo: indigo
6
  sdk: docker
7
+ pinned: true
8
+ license: mit
9
+ short_description: A simple yet comprehensive Flask-based user authentication.
10
  ---
11
 
12
  Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
13
+
14
+ ---
15
+
16
+ # Flask Login System 🔐
17
+
18
+ A simple yet comprehensive Flask-based user authentication system with SQLite database integration, featuring user registration, login, session management, and "Remember Me" functionality.
19
+
20
+ **Live Demo:** [https://rahul23232-flask-login.hf.space/](https://rahul23232-flask-login.hf.space/)
21
+
22
+ ## 📋 Table of Contents
23
+
24
+ - [Features](#features)
25
+ - [Technologies Used](#technologies-used)
26
+ - [Installation](#installation)
27
+ - [Usage](#usage)
28
+ - [Project Structure](#project-structure)
29
+ - [API Routes](#api-routes)
30
+ - [Database Schema](#database-schema)
31
+ - [Security Considerations](#security-considerations)
32
+ - [Contributing](#contributing)
33
+ - [License](#license)
34
+
35
+ ## ✨ Features
36
+
37
+ - **User Registration**: Create new user accounts with unique usernames
38
+ - **User Authentication**: Secure login system with credential verification
39
+ - **Session Management**: Server-side session handling for user state
40
+ - **Remember Me**: Optional persistent login that survives browser restarts
41
+ - **Cookie Management**: Last visit tracking with customizable expiration
42
+ - **SQLite Integration**: Lightweight database for user storage
43
+ - **Responsive Design**: Clean, user-friendly interface
44
+ - **Error Handling**: Proper validation and error messages
45
+
46
+ ## 🛠️ Technologies Used
47
+
48
+ - **Backend**: Python 3.x, Flask
49
+ - **Database**: SQLite3
50
+ - **Frontend**: HTML, CSS (Bootstrap-compatible)
51
+ - **Session Management**: Flask Sessions
52
+ - **Deployment**: Hugging Face Spaces
53
+
54
+ ## 📦 Installation
55
+
56
+ ### Prerequisites
57
+
58
+ - Python 3.7 or higher
59
+ - pip (Python package installer)
60
+
61
+ ### Local Setup
62
+
63
+ 1. **Clone the repository**
64
+ ```bash
65
+ git clone https://github.com/yourusername/flask-login-system.git
66
+ cd flask-login-system
67
+ ```
68
+
69
+ 2. **Install dependencies**
70
+ ```bash
71
+ pip install flask
72
+ ```
73
+
74
+ 3. **Run the application**
75
+ ```bash
76
+ python app.py
77
+ ```
78
+
79
+ 4. **Access the application**
80
+ - Open your browser and navigate to `http://localhost:5000`
81
+
82
+ ### Docker Setup (for Hugging Face Spaces)
83
+
84
+ The project includes Docker configuration for deployment on Hugging Face Spaces:
85
+
86
+ ```dockerfile
87
+ FROM python:3.9-slim
88
+
89
+ WORKDIR /app
90
+
91
+ COPY requirements.txt .
92
+ RUN pip install -r requirements.txt
93
+
94
+ COPY . .
95
+
96
+ EXPOSE 7860
97
+
98
+ CMD ["python", "app.py"]
99
+ ```
100
+
101
+ ## 🎯 Usage
102
+
103
+ ### Getting Started
104
+
105
+ 1. **Access the Application**: Navigate to the home URL
106
+ 2. **Create Account**: Click "Sign Up" to create a new user account
107
+ 3. **Login**: Use your credentials to log in
108
+ 4. **Remember Me**: Check the "Remember Me" option to stay logged in
109
+ 5. **Logout**: Click "Logout" to end your session
110
+
111
+ ### User Flow
112
+
113
+ ```mermaid
114
+ graph TD
115
+ A[Visit Homepage] --> B{User Logged In?}
116
+ B -->|No| C[Redirect to Login]
117
+ B -->|Yes| D[Show Dashboard]
118
+ C --> E[Login Form]
119
+ E --> F[Submit Credentials]
120
+ F --> G{Valid Credentials?}
121
+ G -->|No| H[Show Error]
122
+ G -->|Yes| I[Create Session]
123
+ I --> J{Remember Me?}
124
+ J -->|Yes| K[Set Permanent Session]
125
+ J -->|No| L[Set Temporary Session]
126
+ K --> D
127
+ L --> D
128
+ D --> M[Logout Option]
129
+ M --> N[Clear Session & Cookies]
130
+ N --> C
131
+ ```
132
+
133
+ ## 📁 Project Structure
134
+
135
+ ```
136
+ flask-login-system/
137
+ ├── app.py # Main Flask application
138
+ ├── templates/ # HTML templates
139
+ │ ├── base.html # Base template
140
+ │ ├── login.html # Login page
141
+ │ ├── signup.html # Registration page
142
+ │ └── home.html # Dashboard/home page
143
+ ├── static/ # Static files (CSS, JS, images)
144
+ │ └── style.css # Custom styles
145
+ ├── users.db # SQLite database (created automatically)
146
+ ├── requirements.txt # Python dependencies
147
+ ├── Dockerfile # Docker configuration
148
+ ├── README.md # Project documentation
149
+ └── .gitignore # Git ignore rules
150
+ ```
151
+
152
+ ## 🛣️ API Routes
153
+
154
+ ### Public Routes
155
+
156
+ | Route | Method | Description | Parameters |
157
+ |-------|---------|-------------|------------|
158
+ | `/login` | GET, POST | User login page | `username`, `password`, `remember` |
159
+ | `/signup` | GET, POST | User registration | `username`, `password` |
160
+
161
+ ### Protected Routes
162
+
163
+ | Route | Method | Description | Authentication Required |
164
+ |-------|---------|-------------|------------------------|
165
+ | `/` | GET | Homepage/Dashboard | Yes |
166
+ | `/logout` | GET | User logout | Yes |
167
+
168
+ ### Route Details
169
+
170
+ #### `/` (Homepage)
171
+ - **Method**: GET
172
+ - **Authentication**: Required
173
+ - **Description**: Main dashboard showing welcome message and last visit info
174
+ - **Response**: Redirects to login if not authenticated
175
+
176
+ #### `/signup` (Registration)
177
+ - **Methods**: GET, POST
178
+ - **Parameters**:
179
+ - `username` (string): Unique username
180
+ - `password` (string): User password
181
+ - **Validation**: Username must be unique
182
+ - **Response**: Redirects to login on success
183
+
184
+ #### `/login` (Authentication)
185
+ - **Methods**: GET, POST
186
+ - **Parameters**:
187
+ - `username` (string): User's username
188
+ - `password` (string): User's password
189
+ - `remember` (checkbox): Optional "Remember Me"
190
+ - **Response**: Redirects to homepage on success
191
+
192
+ #### `/logout` (Session Termination)
193
+ - **Method**: GET
194
+ - **Description**: Clears session and cookies
195
+ - **Response**: Redirects to login page
196
+
197
+ ## 🗄️ Database Schema
198
+
199
+ ### Users Table
200
+
201
+ ```sql
202
+ CREATE TABLE users (
203
+ id INTEGER PRIMARY KEY AUTOINCREMENT,
204
+ username TEXT UNIQUE NOT NULL,
205
+ password TEXT NOT NULL
206
+ );
207
+ ```
208
+
209
+ | Column | Type | Constraints | Description |
210
+ |--------|------|-------------|-------------|
211
+ | `id` | INTEGER | PRIMARY KEY, AUTOINCREMENT | Unique user identifier |
212
+ | `username` | TEXT | UNIQUE, NOT NULL | User's login name |
213
+ | `password` | TEXT | NOT NULL | User's password (plain text) |
214
+
215
+ ### Database Operations
216
+
217
+ - **Connection**: SQLite3 with `sqlite3.Row` factory for dictionary-like access
218
+ - **Initialization**: Automatic table creation on first run
219
+ - **Queries**: Parameterized queries to prevent SQL injection
220
+
221
+ ## 🔒 Security Considerations
222
+
223
+ ### Current Implementation
224
+
225
+ - ✅ SQL injection protection via parameterized queries
226
+ - ✅ Session-based authentication
227
+ - ✅ CSRF protection through Flask's secret key
228
+ - ✅ Input validation and error handling
229
+
230
+ ### Production Recommendations
231
+
232
+ - ⚠️ **Password Hashing**: Currently stores plain text passwords
233
+ ```python
234
+ from werkzeug.security import generate_password_hash, check_password_hash
235
+
236
+ # For registration
237
+ hashed_password = generate_password_hash(password)
238
+
239
+ # For login verification
240
+ check_password_hash(stored_hash, provided_password)
241
+ ```
242
+
243
+ - ⚠️ **Environment Variables**: Move secret key to environment variables
244
+ ```python
245
+ import os
246
+ app.secret_key = os.environ.get('SECRET_KEY', 'fallback-secret-key')
247
+ ```
248
+
249
+ - ⚠️ **HTTPS**: Enable HTTPS in production
250
+ - ⚠️ **Rate Limiting**: Implement login attempt limits
251
+ - ⚠️ **Input Validation**: Add comprehensive input sanitization
252
+ - ⚠️ **Session Security**: Configure secure session cookies
253
+
254
+ ### Recommended Security Enhancements
255
+
256
+ ```python
257
+ # Enhanced security configuration
258
+ app.config.update(
259
+ SESSION_COOKIE_SECURE=True, # HTTPS only
260
+ SESSION_COOKIE_HTTPONLY=True, # No JS access
261
+ SESSION_COOKIE_SAMESITE='Lax', # CSRF protection
262
+ PERMANENT_SESSION_LIFETIME=timedelta(hours=1) # Shorter sessions
263
+ )
264
+ ```
265
+
266
+ ## 🎨 Frontend Templates
267
+
268
+ ### Template Structure
269
+
270
+ All templates extend `base.html` for consistent styling:
271
+
272
+ ```html
273
+ <!-- base.html -->
274
+ <!DOCTYPE html>
275
+ <html lang="en">
276
+ <head>
277
+ <meta charset="UTF-8">
278
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
279
+ <title>{% block title %}Flask Login System{% endblock %}</title>
280
+ <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.1.3/dist/css/bootstrap.min.css" rel="stylesheet">
281
+ </head>
282
+ <body>
283
+ <div class="container mt-4">
284
+ {% block content %}{% endblock %}
285
+ </div>
286
+ </body>
287
+ </html>
288
+ ```
289
+
290
+ ### Form Examples
291
+
292
+ #### Login Form
293
+ ```html
294
+ <form method="POST">
295
+ <div class="mb-3">
296
+ <label for="username" class="form-label">Username</label>
297
+ <input type="text" class="form-control" name="username" required>
298
+ </div>
299
+ <div class="mb-3">
300
+ <label for="password" class="form-label">Password</label>
301
+ <input type="password" class="form-control" name="password" required>
302
+ </div>
303
+ <div class="mb-3 form-check">
304
+ <input type="checkbox" class="form-check-input" name="remember">
305
+ <label class="form-check-label">Remember Me</label>
306
+ </div>
307
+ <button type="submit" class="btn btn-primary">Login</button>
308
+ </form>
309
+ ```
310
+
311
+ ## 🚀 Deployment
312
+
313
+ ### Hugging Face Spaces
314
+
315
+ The project is configured for deployment on Hugging Face Spaces:
316
+
317
+ 1. **Create Space**: Create a new Space on Hugging Face
318
+ 2. **Upload Files**: Push your code to the Space repository
319
+ 3. **Configuration**: Ensure `app.py` runs on port 7860
320
+ 4. **Environment**: The Space will automatically build and deploy
321
+
322
+ ### Local Development
323
+
324
+ ```bash
325
+ # Development mode with auto-reload
326
+ export FLASK_ENV=development
327
+ export FLASK_DEBUG=1
328
+ python app.py
329
+ ```
330
+
331
+ ### Production Deployment
332
+
333
+ ```bash
334
+ # Use a production WSGI server
335
+ pip install gunicorn
336
+ gunicorn -w 4 -b 0.0.0.0:5000 app:app
337
+ ```
338
+
339
+ ## 🤝 Contributing
340
+
341
+ 1. Fork the repository
342
+ 2. Create a feature branch (`git checkout -b feature/amazing-feature`)
343
+ 3. Commit your changes (`git commit -m 'Add amazing feature'`)
344
+ 4. Push to the branch (`git push origin feature/amazing-feature`)
345
+ 5. Open a Pull Request
346
+
347
+ ### Development Guidelines
348
+
349
+ - Follow PEP 8 style guidelines
350
+ - Add comments for complex logic
351
+ - Update documentation for new features
352
+ - Test all functionality before submitting
353
+
354
+ ## 📝 License
355
+
356
+ This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
357
+
358
+ ## 🐛 Known Issues
359
+
360
+ - Plain text password storage (security concern)
361
+ - No password strength validation
362
+ - No account recovery mechanism
363
+ - Limited input sanitization
364
+
365
+ ## 🔮 Future Enhancements
366
+
367
+ - [ ] Password hashing with bcrypt/scrypt
368
+ - [ ] Email verification system
369
+ - [ ] Password reset functionality
370
+ - [ ] User profile management
371
+ - [ ] Role-based access control
372
+ - [ ] OAuth integration (Google, GitHub)
373
+ - [ ] Rate limiting and brute force protection
374
+ - [ ] Advanced session management
375
+ - [ ] API endpoints for mobile apps
376
+ - [ ] Unit and integration tests
377
+
378
+ ## 📞 Support
379
+
380
+ For questions, issues, or contributions:
381
+
382
+ - **Repository**: [GitHub Repository](https://github.com/yourusername/flask-login-system)
383
+ - **Live Demo**: [Flask Login System](https://rahul23232-flask-login.hf.space/)
384
+ - **Issues**: Use GitHub Issues for bug reports and feature requests
385
+
386
+ ---
387
+
388
+ **Note**: This is a demonstration project for educational purposes. For production use, implement proper security measures including password hashing, HTTPS, and comprehensive input validation.
app.py ADDED
@@ -0,0 +1,112 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ from flask import Flask, render_template, request, redirect, url_for, session, make_response
2
+ import sqlite3
3
+ from datetime import timedelta
4
+
5
+ # Flask app setup
6
+ app = Flask(__name__)
7
+ app.secret_key = "supersecretkey" # Change this to a secure key in production
8
+ app.permanent_session_lifetime = timedelta(days=7)
9
+
10
+
11
+ # Helper function to connect to SQLite database
12
+ def get_db_connection():
13
+ conn = sqlite3.connect("users.db")
14
+ conn.row_factory = sqlite3.Row
15
+ return conn
16
+
17
+
18
+ # Initialize database with users table
19
+ def init_db():
20
+ conn = get_db_connection()
21
+ conn.execute("""
22
+ CREATE TABLE IF NOT EXISTS users (
23
+ id INTEGER PRIMARY KEY AUTOINCREMENT,
24
+ username TEXT UNIQUE NOT NULL,
25
+ password TEXT NOT NULL
26
+ )
27
+ """)
28
+ conn.commit()
29
+ conn.close()
30
+
31
+ # Initialize DB at startup
32
+ init_db()
33
+
34
+
35
+ # Home page — only accessible if logged in
36
+ @app.route("/")
37
+ def home():
38
+ if "username" in session:
39
+ username = session["username"]
40
+ last_visit = request.cookies.get("last_visit", "First time visiting!")
41
+ return render_template("home.html", username=username, last_visit=last_visit)
42
+ return redirect(url_for("login"))
43
+
44
+
45
+ # Signup page
46
+ @app.route("/signup", methods=["GET", "POST"])
47
+ def signup():
48
+ if request.method == "POST":
49
+ username = request.form["username"]
50
+ password = request.form["password"]
51
+
52
+ conn = get_db_connection()
53
+ try:
54
+ conn.execute("INSERT INTO users (username, password) VALUES (?, ?)", (username, password))
55
+ conn.commit()
56
+ conn.close()
57
+ return redirect(url_for("login"))
58
+ except sqlite3.IntegrityError:
59
+ return "Username already exists! Try another."
60
+
61
+ return render_template("signup.html")
62
+
63
+
64
+ # Login page
65
+ @app.route("/login", methods=["GET", "POST"])
66
+ def login():
67
+ if request.method == "POST":
68
+ username = request.form["username"]
69
+ password = request.form["password"]
70
+ remember = request.form.get("remember")
71
+
72
+ conn = get_db_connection()
73
+ user = conn.execute(
74
+ "SELECT * FROM users WHERE username=? AND password=?",
75
+ (username, password)
76
+ ).fetchone()
77
+ conn.close()
78
+
79
+ if user:
80
+ session.permanent = (remember == "on")
81
+ session["username"] = username
82
+
83
+ resp = make_response(redirect(url_for("portfolio")))
84
+ resp.set_cookie("last_visit", "Welcome back, " + username,
85
+ max_age=(7*24*60*60 if remember == "on" else None))
86
+ return resp
87
+ else:
88
+ return "Invalid username or password. Try again."
89
+ return render_template("login.html")
90
+
91
+
92
+ # Portfolio page - accessible only if logged in
93
+ @app.route("/portfolio")
94
+ def portfolio():
95
+ username = session.get("username")
96
+ if not username:
97
+ return redirect(url_for("login"))
98
+ return render_template("portfolio.html", username=username)
99
+
100
+
101
+ # Logout route
102
+ @app.route("/logout")
103
+ def logout():
104
+ session.pop("username", None)
105
+ resp = make_response(redirect(url_for("login")))
106
+ resp.set_cookie("last_visit", "", expires=0)
107
+ return resp
108
+
109
+
110
+ # Run the app
111
+ if __name__ == "__main__":
112
+ app.run(debug=True, host="0.0.0.0", port=5000)
requirements.txt ADDED
@@ -0,0 +1,4 @@
 
 
 
 
 
1
+ flask
2
+ gunicorn
3
+ requests
4
+ datetime
users.db ADDED
Binary file (16.4 kB). View file