Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

Β 

History

36 Commits
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 
Β 

Repository files navigation

DevDock

A developer journal application built with React and Node.js, allowing developers to create, organize, and manage their coding journals with tags, search, and analytics.

πŸš€ Features

  • User Authentication: Secure JWT-based authentication with refresh tokens
  • Journal Management: Create, edit, delete, and organize your coding journals
  • Tag System: Organize journals with custom tags
  • Search & Filter: Find journals by title, content, tags, or date range
  • Dashboard Analytics: View statistics about your journaling activity
  • Admin Panel: Manage tags and system settings (admin users only)
  • API Documentation: Swagger/OpenAPI documentation for all endpoints

πŸ“‹ Prerequisites

Before you begin, ensure you have the following installed:

  • Node.js (v18 or higher)
  • npm or yarn
  • MySQL (v8.0 or higher)
  • Redis (v6.0 or higher)
  • Git

πŸ› οΈ Installation

1. Clone the Repository

git clone <repository-url>
cd Devock

2. Database Setup

Create MySQL Database

mysql -u root -p
CREATE DATABASE devdock;
EXIT;

Run Database Schema

mysql -u root -p devdock < Database/schema.sql

Important Note: The schema may need a Role column added to the User table. If you encounter errors about missing Role column, run:

ALTER TABLE User ADD COLUMN Role ENUM('user', 'admin') DEFAULT 'user';

(Optional) Seed Sample Data

mysql -u root -p devdock < Database/seed.sql

3. Backend Setup

cd Backend
npm install

Create Backend Environment File

Create a .env file in the Backend directory:

# Server Configuration
PORT=4000
NODE_ENV=development

# Database Configuration
DB_HOST=localhost
DB_USER=root
DB_PASS=your_mysql_password
DB_NAME=devdock

# JWT Configuration
JWT_SECRET=your-super-secret-jwt-key-change-this-in-production
REFRESH_SECRET=your-refresh-token-secret-key-change-this-in-production

# Redis Configuration
REDIS_URL=redis://127.0.0.1:6379

⚠️ Security Warning:

  • NEVER commit .env files to version control
  • Use strong, random secrets in production
  • JWT_SECRET should be a long, random string (minimum 32 characters)
  • REFRESH_SECRET can be different from JWT_SECRET for added security
  • If REFRESH_SECRET is not set, it will use JWT_SECRET + '_refresh' as fallback

Start Redis Server

# On macOS (using Homebrew)
brew services start redis

# On Linux
sudo systemctl start redis

# On Windows (using WSL or native Redis)
redis-server

Verify Redis is running:

redis-cli ping
# Should return: PONG

4. Frontend Setup

cd ../Frontend
npm install

Frontend Configuration

The frontend is configured to connect to http://localhost:4000 by default. If your backend runs on a different port, update the API URLs in the frontend code.

πŸš€ Running the Application

Start Backend Server

cd Backend
node src/server.js

The backend will start on http://localhost:4000

API Documentation: Once the server is running, visit http://localhost:4000/api-docs for Swagger documentation.

Start Frontend Development Server

cd Frontend
npm run dev

The frontend will start on http://localhost:5173 (or another port if 5173 is occupied)

πŸ“ Project Structure

Devock/
β”œβ”€β”€ Backend/
β”‚   β”œβ”€β”€ src/
β”‚   β”‚   β”œβ”€β”€ app.js                 # Express app configuration
β”‚   β”‚   β”œβ”€β”€ server.js              # Server entry point
β”‚   β”‚   β”œβ”€β”€ config/                # Configuration files
β”‚   β”‚   β”‚   β”œβ”€β”€ redis.js          # Redis client setup
β”‚   β”‚   β”‚   └── swagger.js        # API documentation config
β”‚   β”‚   β”œβ”€β”€ db/
β”‚   β”‚   β”‚   └── pool.js           # MySQL connection pool
β”‚   β”‚   β”œβ”€β”€ middleware/           # Express middleware
β”‚   β”‚   β”‚   β”œβ”€β”€ auth.middleware.js
β”‚   β”‚   β”‚   β”œβ”€β”€ admin.middleware.js
β”‚   β”‚   β”‚   └── checkTokenRevoked.js
β”‚   β”‚   β”œβ”€β”€ modules/               # Feature modules
β”‚   β”‚   β”‚   β”œβ”€β”€ auth/             # Authentication
β”‚   β”‚   β”‚   β”œβ”€β”€ journals/         # Journal management
β”‚   β”‚   β”‚   β”œβ”€β”€ tag/              # Tag management
β”‚   β”‚   β”‚   β”œβ”€β”€ dashboard/        # Dashboard analytics
β”‚   β”‚   β”‚   └── admin/            # Admin features
β”‚   β”‚   └── utils/
β”‚   β”‚       β”œβ”€β”€ jwt.js            # JWT token utilities
β”‚   β”‚       └── logger.js        # Winston logger
β”‚   └── package.json
β”œβ”€β”€ Frontend/
β”‚   β”œβ”€β”€ src/
β”‚   β”‚   β”œβ”€β”€ App.jsx              # Main app component
β”‚   β”‚   β”œβ”€β”€ Login.jsx            # Login page
β”‚   β”‚   β”œβ”€β”€ Signup.jsx           # Signup page
β”‚   β”‚   β”œβ”€β”€ Home.jsx             # Main journal interface
β”‚   β”‚   β”œβ”€β”€ DashboardPage.jsx    # Analytics dashboard
β”‚   β”‚   β”œβ”€β”€ AdminPage.jsx        # Admin panel
β”‚   β”‚   └── Components/          # Reusable components
β”‚   └── package.json
└── Database/
    β”œβ”€β”€ schema.sql               # Database schema
    └── seed.sql                # Sample data

πŸ” Authentication & Security

JWT Token System

The application uses a dual-token authentication system:

  • Access Token: Short-lived (15 minutes), used for API requests
  • Refresh Token: Long-lived (7 days), stored in httpOnly cookie, used to get new access tokens

How It Works

  1. Login/Signup: User receives an access token (in response) and a refresh token (in httpOnly cookie)
  2. API Requests: Include access token in Authorization: Bearer <token> header
  3. Token Expiry: When access token expires, frontend can call /api/auth/refresh to get a new one
  4. Logout: Both tokens are revoked

Environment Variables Security

Required for Production:

  • Use strong, randomly generated secrets
  • Never share or commit secrets
  • Use different secrets for development and production
  • Consider using environment variable management services (AWS Secrets Manager, etc.)

πŸ“‘ API Endpoints

Authentication

  • POST /api/auth/signup - Register new user
  • POST /api/auth/login - Login user
  • POST /api/auth/refresh - Refresh access token
  • POST /api/auth/logout - Logout user

Journals

  • GET /api/journals - Get user's journals (paginated)
  • POST /api/journals - Create new journal
  • PUT /api/journals/:id - Update journal
  • DELETE /api/journals/:id - Delete journal
  • GET /api/journals/filter - Filter/search journals

Tags

  • GET /api/tags - Get all tags
  • POST /api/tags - Create new tag
  • PUT /api/tags/:id - Update tag
  • DELETE /api/tags/:id - Delete tag

Dashboard

  • GET /api/dashboard/journals-count - Get journal statistics
  • GET /api/dashboard/tag-usage - Get tag usage statistics
  • GET /api/dashboard/activity/hourly - Get hourly activity

Admin

  • GET /api/admin/tags - Get all tags (admin)
  • POST /api/admin/tags - Create tag (admin)
  • DELETE /api/admin/tags/:id - Delete tag (admin)

Full API Documentation: Visit http://localhost:4000/api-docs when the server is running.

πŸ§ͺ Testing

Manual Testing Checklist

  1. Authentication

    • Sign up with new user
    • Login with existing user
    • Access token expires after 15 minutes
    • Refresh token works to get new access token
    • Logout revokes both tokens
  2. Journals

    • Create journal
    • Edit journal
    • Delete journal
    • Search/filter journals
    • Pagination works
  3. Tags

    • Create tags
    • Assign tags to journals
    • Filter by tags
  4. Dashboard

    • View statistics
    • View activity charts

πŸ› Troubleshooting

Database Connection Issues

Error: ER_ACCESS_DENIED_ERROR or ECONNREFUSED

  • Check MySQL is running: mysql -u root -p
  • Verify credentials in .env file
  • Ensure database exists: SHOW DATABASES;

Redis Connection Issues

Error: Redis Client Error or connection refused

  • Check Redis is running: redis-cli ping
  • Verify REDIS_URL in .env file
  • Start Redis: redis-server or brew services start redis

JWT Token Errors

Error: Invalid or expired token

  • Check JWT_SECRET is set in .env
  • Verify token hasn't expired (access tokens expire in 15 minutes)
  • Try logging in again to get new tokens

Missing Role Column

Error: Unknown column 'Role' in 'field list'

  • Run: ALTER TABLE User ADD COLUMN Role ENUM('user', 'admin') DEFAULT 'user';

Port Already in Use

Error: EADDRINUSE: address already in use

  • Change PORT in .env file
  • Or kill the process using the port:
    # Find process
    lsof -i :4000
    # Kill process
    kill -9 <PID>

CORS Errors

Error: CORS policy blocked

  • Verify frontend origin is in app.js CORS configuration
  • Check credentials: true is set in CORS config

πŸ”§ Development

Adding New Features

  1. Create module in Backend/src/modules/
  2. Add routes in Backend/src/app.js
  3. Update Swagger documentation
  4. Test endpoints

Code Style

  • Backend: Follow existing Express.js patterns
  • Frontend: Follow React functional component patterns
  • Use async/await for asynchronous operations
  • Handle errors appropriately

πŸ“ Notes

  • Refresh Tokens: Stored in Redis for revocation tracking
  • Access Tokens: Stored in localStorage (frontend)
  • Cookies: Refresh tokens sent as httpOnly cookies for security
  • Password Hashing: Uses bcrypt with 15 rounds
  • Logging: Winston logger configured (check Backend/logs/)

🀝 Contributing

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Commit your changes (git commit -m 'Add some amazing feature')
  4. Push to the branch (git push origin feature/amazing-feature)
  5. Open a Pull Request

πŸ“„ License

This project is licensed under the MIT License.
See the LICENSE file for details.

πŸ‘₯ Author

  • Adham Kiwan

πŸ™ Acknowledgments

  • Express.js
  • React
  • MySQL
  • Redis
  • JWT

Need Help? Open an issue on GitHub or contact the maintainers.

About

A developer journal application built with React and Node.js, allowing developers to create, organize, and manage their coding journals with tags, search, and analytics.

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages