Installation and Login Session

Install Node (node --version)

npx create-react-app my-app
cd my-app
npm start

Delete all file except index.html in public folder

Delete all file except index.js in src folder

Remove unwanted code in index.html and index.js

download template and then use this comment npm install for dependeies download then run npm start and npm run dev

Login Session

npm install react-router-dom
import React, { useState, useEffect } from 'react';
import { BrowserRouter as Router, Route, Routes, Navigate } from 'react-router-dom';

const mockUsers = [
  { username: "user1", password: "pass123" },
  { username: "user2", password: "secure456" },
  { username: "user3", password: "mypassword" }
];

const Login = ({ onLogin }) => {
  const [username, setUsername] = useState('');
  const [password, setPassword] = useState('');
  const handleSubmit = (e) => {
    e.preventDefault();
    const user = mockUsers.find(u => u.username === username && u.password === password);
    if (user) {
      onLogin(user.username);
    } else {
      alert('Invalid credentials');
    }
  };

  return (
    <div>
      <h2>Login</h2>
      <form onSubmit={handleSubmit}>
        <input type="text" placeholder="Username" value={username} onChange={(e) => setUsername(e.target.value)} required />
        <input type="password" placeholder="Password" value={password} onChange={(e) => setPassword(e.target.value)} required />
        <button type="submit">Login</button>
      </form>
    </div>
  );
};

const Dashboard = ({ user, onLogout }) => {
  useEffect(() => {
    const timer = setTimeout(() => {
      alert('Session expired. Logging out.');
      onLogout();
    }, 60000); // 1 minute session timeout

    return () => clearTimeout(timer);
  }, [onLogout]);

  return (
    <div>
      <h2>Welcome, {user}!</h2>
      <button onClick={onLogout}>Logout</button>
    </div>
  );
};

const App = () => {
  const [user, setUser] = useState(() => {
    return localStorage.getItem('user') || null; 
  });

  useEffect(() => {
    if (user) {
      localStorage.setItem('user', user); 
    } else {
      localStorage.removeItem('user'); 
    }
  }, [user]);

  const handleLogin = (username) => {
    setUser(username);
  };

  const handleLogout = () => {
    setUser(null);
  };

  return (
    <Router>
      <div>
        {user ? (
          <Routes>
            <Route path="/dashboard" element={<Dashboard user={user} onLogout={handleLogout} />} />
            <Route path="/" element={<Navigate to="/dashboard" replace />} />
            <Route path="/login" element={<Navigate to="/dashboard" replace />} />
          </Routes>
        ) : (
          <Routes>
            <Route path="/login" element={<Login onLogin={handleLogin} />} />
            <Route path="*" element={<Navigate to="/login" replace />} />
          </Routes>
        )}
      </div>
    </Router>
  );
};

export default App;

Validation

      const validation = () => {
      let errors ={}
        if(!username.trim()){
          errors.username = "Username is required"
        }
        if(!password.trim()){
          errors.password = "Password is required"
        }
        return errors
      }

      const handleSubmit = (e) => {
        e.preventDefault();

        const validationForm = validation()

        if(Object.keys(validationForm).length > 0){
          setErrors(validationForm)
        } else {
          //
        }    
      };

      {errors.username && <span className="errors ps-3">{errors.username}</span>}
    

toastify

          npm install react-toastify


          import React from "react";
          import { ToastContainer, toast } from "react-toastify";
          import "react-toastify/dist/ReactToastify.css";

          const App = () => {
            const showToast = () => {
              toast.success("This is a success alert!");
              toast.error("This is an error alert!");
              toast.warning("This is a warning alert!");
              toast.info("This is an info alert!");
            };

            return (
              <div>
                <h2>React Toast Alert Example</h2>
                <button onClick={showToast}>Show Toast</button>
                <ToastContainer position="top-right" autoClose={3000} />
              </div>
            );
          };

          export default App; 
    

Menu - Navigation, Link, Active Class,...

          npm install react-router-dom


          import React from 'react';
          import { Link, useLocation, useNavigate } from "react-router-dom";

          const Header = () => {  
            const location = useLocation(); // Get current path
            const navigate = useNavigate(); // Hook for navigation

            // Function to handle navigation and set active class
            const handleNavigation = (path) => {
              navigate('./page2'); // Navigate to selected path
            };

            const isCreatePage = location.pathname.includes('/create'); // Check if '/create' is in the path

            return (
              <div className="header-wrapper">
                <div className="nav-bar p-2">
                  <ul type="none">
                    <li className={location.pathname === "/" ? "active" : ""} onClick={() => handleNavigation("/")}>
                      <Link to="/">Home</Link>
                    </li>
                    <li className={location.pathname === "/page2" ? "active" : ""} onClick={() => handleNavigation("/page2")}>
                      <Link to="/page2">Page 2</Link>
                    </li>
                  </ul>
                </div>
              </div>
            );
          };

          export default Header;
    

Tooltip

          import React from 'react';
          import { Tooltip, OverlayTrigger, Button } from 'react-bootstrap';

          const TooltipExample = () => {
            return (
              <div className="d-flex justify-content-center align-items-center" style={{ height: '100vh' }}>
                <OverlayTrigger
                  placement="top"
                  overlay={<Tooltip id="tooltip-top">This is a tooltip!</Tooltip>}
                >
                  <Button variant="primary">Hover me!</Button>
                </OverlayTrigger>
              </div>
            );
          };

          export default TooltipExample;
    

ENV - Environment Variables

          .env (root path, package.json file folder)
          REACT_APP_API_URL= https://67cd5231dd7651e464ee0981.mockapi.io/Gobudget/

          
          const apiUrl = process.env.REACT_APP_API_URL;
          <h2>Welcome, {apiUrl}</h2>

          //server restart
    

Axios

          import axios from 'axios';

          // 
          useEffect(() => {
        axios.get(`${process.env.REACT_APP_API_URL}Category`)
          .then(response => {
            setCategoryData(response.data);
          })
          .catch(error => {
            console.error('Error fetching data: ', error);
          });
      }, []);


      // Image file also sent
      axios.post(url, editRowData, {
            headers: {
                'Content-Type': 'multipart/form-data',
            },
            })
            .then(response => {
                console.log('File successfully uploaded:', response.data);
                onDataReceived(false);
                window.location.reload();
    
            })
            .catch(error => {
                console.error('Error uploading file:', error);
            });
    

Create Form

          import React, { useState, useEffect } from 'react';
import { Row, Col, FloatingLabel, Tooltip, OverlayTrigger,
  Form, Dropdown, DropdownButton,
  Button, ButtonGroup, Modal } from 'react-bootstrap';
import axios from 'axios';
import { toast, ToastContainer } from "react-toastify";
import "react-toastify/dist/ReactToastify.css";

import category1Icon from '../../dist/images/icons/categories/1.png'
import category2Icon from '../../dist/images/icons/categories/2.png'
import category3Icon from '../../dist/images/icons/categories/3.png'
import category4Icon from '../../dist/images/icons/categories/4.png'
import category5Icon from '../../dist/images/icons/categories/5.png'
import category6Icon from '../../dist/images/icons/categories/6.png'
import category7Icon from '../../dist/images/icons/categories/7.png'
import category8Icon from '../../dist/images/icons/categories/8.png'
import category9Icon from '../../dist/images/icons/categories/9.png'

const App = () => {
  const apiUrl = process.env.REACT_APP_API_URL;

  const [addShow, setAddShow] = useState(true);
  const handleAddClose = () => onCloseFrom();
  const handleAddShow = () => setAddShow(true);

  const onCloseFrom = () => {
    setCategoryName("");
    setCategoryIcon("");
    setCategoryType(""); 
    setError({});
    setAddShow(false)
  }

  


  const [categoryName, setCategoryName] = useState("");
  const [CategoryIcon, setCategoryIcon] = useState("");
  const [CategoryType, setCategoryType] = useState("1"); 
  const [error, setError] = useState({});

  const categoryIcons = {
    1: category1Icon,
    2: category2Icon,
    3: category3Icon,
    4: category4Icon,
    5: category5Icon,
    6: category6Icon,
    7: category7Icon,
    8: category8Icon,
    9: category9Icon,
  };

  const FormSuccess = () =>
    toast.success("Successfully logged in", {
      onClose: () => {},
    });

  const validation = () => {
    const newError = {};
    if (!categoryName.trim()) {
      newError.categoryName = "Category Name is required";
    }
    if (!CategoryIcon) {
      newError.CategoryIcon = "Category Icon is required";
    }
    if (!CategoryType) {
      newError.CategoryType = "Category Type is required"; 
    }
    return newError;
  };

  const handleCreateTemplateSubmit = async (e) => {
    e.preventDefault();
    const validationForm = validation();

    if (Object.keys(validationForm).length > 0) {
      setError(validationForm);
    } else {
      const formData = {
        Category: categoryName,
        Category_img_id: CategoryIcon,
        Category_type: CategoryType, 
      };

      axios
        .post(`${apiUrl}/Category/`, formData)
        .then((response) => {
          onCloseFrom()          
          toast.success("Category Created")

        })
        .catch((error) => {
          console.error("Error submitting form:", error, `${process.env.REACT_APP_API}/Category/`, formData);
        });
    }
  };

  return (
    <>
      <Modal show={addShow} size="lg" onHide={handleAddClose} animation={false} centered>
        <Modal.Body>
          <form onSubmit={handleCreateTemplateSubmit} className="bgWhite p-4" id="myForm">
            <Row>
              <Col xs={12}>
                <h4 className="fw-bold mb-5">Create Category</h4>
                <Form.Group className="mb-4 " controlId="floatingInput">
                  <div className="frm-group"> 
                  <Form.Label>Category name</Form.Label>
                  <Form.Control
                    type="text"
                    placeholder="Template *"
                    onChange={(e) => {setCategoryName(e.target.value); error.categoryName = ''}}
                    value={categoryName}
                  />
                  </div>
                  {error.categoryName && <p className="errors mt-2">{error.categoryName}</p>}
                </Form.Group>

                {/* Radio Buttons with Images */}
                <Form.Group className="mb-4">
                  <div className="frm-group">
                  <Form.Label>Category Icon</Form.Label>
                  <div className="d-flex gap-3">
                  {Object.entries(categoryIcons)?.map(([id, icon]) => (
                    <Form.Check type="radio" className="radio-image">
                      <Form.Check.Input
                        type="radio"
                        name="radioGroup"
                        value={id}
                        checked={CategoryIcon === id}
                        onChange={(e) => {setCategoryIcon(e.target.value); error.CategoryIcon = ''}}
                      />
                      <Form.Check.Label>
                        <img
                          src={icon} // Replace with actual image URL
                          alt={id}
                          className="radio-img"
                        />
                      </Form.Check.Label>
                    </Form.Check>

                  ))}  
                  </div> 
                  </div>

                    
                  {error.CategoryIcon && <p className="errors mt-2">{error.CategoryIcon}</p>}
                </Form.Group>

                {/* Dropdown */}
             <Form.Group className="mb-4">
              <div className="frm-group">
                <Form.Label>Type</Form.Label>
                <Form.Select
                  aria-label="Default select example"
                  className="form-control"
                  value={CategoryType || "Select an option"}  // Ensure CategoryType is defined, or use default value
                  onChange={(e) => setCategoryType(e.target.value)}  // Changed onSelect to onChange
                >
                  <option value="1">Income</option>
                  <option value="2">Expense</option>
                </Form.Select>
              </div>
              {error.CategoryType && <p className="error-msg">{error.CategoryType}</p>}
            </Form.Group>

                

                <Col md="auto" className="text-end">
                  <button type="submit" className="btn-green my-3">
                    Save
                  </button>
                </Col>
              </Col>
            </Row>
          </form>
          
        </Modal.Body>
      </Modal>
    </>
  );
};

export default App;
    

Delete data

const [showDeleteMsgPopup, setShowDeleteMsgPopup] = useState(false);
  const [dataDeleteId, setDataDeleteId,] = useState(null);


  onClick={() => handleDeleteTemplate(data.id)}

   const handleDeleteTemplate = (deleteId) => {

    setShowDeleteMsgPopup(true);
    const deleteID = deleteId;
    setDataDeleteId(deleteID)
    console.log(deleteID);
  };

  const handleProposalDeleteCancelled = () => {
    setShowDeleteMsgPopup(false);
  }

  const handleProposalDeleteConfirmed = () => {
    setShowDeleteMsgPopup(false);
    console.log('Delete', dataDeleteId);
    axios.delete(`${process.env.REACT_APP_API}proposal/template_management/${dataDeleteId}/`)
      .then(response => {
        console.log('Deleted');
        setDataDeleteId(null)        
        
        if(response.data.status === "GD_02") {            
          toast.error(response.data.message);            
          } else {
            toast.success(response.data.message);
            fetchData()
          } 
      })
      .catch(error => {
        console.log('Delete Data Error', error);
      });

    }
  
      <Modal show={showDeleteMsgPopup} onHide={handleProposalDeleteCancelled}>
      <Modal.Body closeButton><h4>Are you sure to delete this Data</h4></Modal.Body>
      <Modal.Footer>
        <button className="btn-green-2" onClick={handleProposalDeleteCancelled}>
          Cancel
        </button>
        <button className="btn-green ms-3" onClick={handleProposalDeleteConfirmed}>
          Delete
        </button>
      </Modal.Footer>
      </Modal>
         
    

Edit data

import { useLocation, useParams, useNavigate } from 'react-router-dom';


const apiUrl = process.env.REACT_APP_API_URL;
  const location = useLocation();
  const navigate = useNavigate();
  const {id} = useParams()
  


  const isCreatePage = location.pathname.includes('/create');

  const [editId, setEditId] = useState(null)


  useEffect(() => {
    if(id){
      setEditId(id)
    }
  }, [id])

  useEffect(() => {
    if(isCreatePage || editId){
      setAddShow(true)
    }
    if(editId){
      fetchEditData()
    }
  }, [isCreatePage, editId])


  const fetchEditData = () => {
    axios.get(`${apiUrl}Category/${editId}`)
    .then(response => {
      // console.log(response.data);
      const data = response.data;
      setCategoryName(data.Category)
      setCategoryIcon(data.Category_img_id)
      setCategoryType(data.Category_type)
    })
    .catch(error => {
      console.error('Error fetching data: ', error,);
    });
  }


  const validation = () => {
    const newError = {};
    if (!categoryName.trim()) {
      newError.categoryName = "Category Name is required";
    }
    if (!CategoryIcon) {
      newError.CategoryIcon = "Category Icon is required";
    }
    if (!CategoryType) {
      newError.CategoryType = "Category Type is required"; 
    }
    return newError;
  };

  const handleCreateTemplateSubmit = async (e) => {
    e.preventDefault();
    const validationForm = validation();

    if (Object.keys(validationForm).length > 0) {
      setError(validationForm);
    } else {
      const formData = {
        Category: categoryName,
        Category_img_id: CategoryIcon,
        Category_type: CategoryType, 
      };

      let sendApi = `${apiUrl}/Category/`
      if (editId) {
        sendApi = `${apiUrl}/Category/${editId}`
      }

      const method = editId ? 'put' : 'post';

      axios({
          method: method, 
          url: sendApi,
          data: formData, 
        })
        .then((response) => {
          onCloseFrom()          
          toast.success("Category Data Submitted")

        })
        .catch((error) => {
          console.error("Error submitting form:", error, `${process.env.REACT_APP_API}/Category/`, formData);
        });
    }
  };
    

Data Grid

import React from "react";
import DataTable from "react-data-table-component";

// Sample data
const data = [
  { id: 1, name: "John Doe", age: 28, email: "john@example.com" },
  { id: 2, name: "Jane Smith", age: 34, email: "jane@example.com" },
  { id: 3, name: "Sam Green", age: 25, email: "sam@example.com" },
];

// Define columns
const columns = [
  {
    name: "ID",
    selector: (row) => row.id,
    sortable: true,
  },
  {
    name: "Name",
    selector: (row) => row.name,
    sortable: true,
  },
  {
    name: "Age",
    selector: (row) => row.age,
    sortable: true,
  },
  {
    name: "Email",
    selector: (row) => row.email,
    // Example of adding HTML inside the cell
    cell: (row) => (
      <a href={`mailto:${row.email}`} dangerouslySetInnerHTML={{ __html: `<span style="color: blue;">${row.email}</span>` }} />
    ),
  },
  {
    name: "Actions",
    cell: (_, index) => (
      <button
        // onClick={() => handleDelete(index)}
        style={{
          backgroundColor: "red",
          color: "white",
          border: "none",
          padding: "5px 10px",
          cursor: "pointer",
        }}
      >
        Delete
      </button>
    ),
  },
];

const MyDataTable = () => {
  return (
    <div>
      <h2>My Data Table</h2>
      <DataTable
        columns={columns}
        data={data}
        pagination
        highlightOnHover
      />
    </div>
  );
};

export default MyDataTable;

Date picker

npm install react-datepicker
npm install date-fns

import React, { useState } from "react";
import DatePicker from "react-datepicker";
import "react-datepicker/dist/react-datepicker.css"; // Import styles for the date picker

const SimpleDatePicker = () => {
  const [selectedDate, setSelectedDate] = useState(null);

  const handleDateChange = (date) => {
    setSelectedDate(date);
  };

  return (
    <div>
      <h2>Select a Date</h2>
      <DatePicker
        selected={selectedDate}
        onChange={handleDateChange}
        dateFormat="MM/dd/yyyy" // Set the format of the date
        placeholderText="Select a date"
      />
    </div>
  );
};

export default SimpleDatePicker;

Datapicker format changes

import DatePicker from 'react-datepicker';
        import { parse, format } from 'date-fns';
        
        
        const start_time : Fri Dec 27 2024 14:00:00 GMT+0530 (India Standard Time)
        
        
        const formatTime = (time) => {
            return new Date(time).toLocaleTimeString('en-GB', { hour: '2-digit', minute: '2-digit' });
        };
        
        const formattime = formatTime(start_time)  // method 1 start_time : "14:00"
        format(start_time, "hh:mm aa")  // method 2 start_time : "2:00 PM"
        
        
        
        
        
        const start_date : Mon Dec 02 2024 00:00:00 GMT+0530 (India Standard Time)
        
        const formatDateToYYYYMMDD = (date) => {
                if (!date) return ''; // handle empty or invalid date
                const year = date.getFullYear();
                const month = String(date.getMonth() + 1).padStart(2, '0'); // Months are 0-based, so add 1
                const day = String(date.getDate()).padStart(2, '0');
                return `${year}-${month}-${day}`;
        };
        
        const formatDate = formatDateToYYYYMMDD(start_date)  // method 1 start_date: "2024-12-02"
        format(start_date, "yyyy-MM-dd")  // method 2 start_date: "2024-12-02"
        
        
        const start_time = 09:00:00
        const convertTimeToDate = (timeString) => {
                const currentDate = new Date();
                const [hours, minutes, seconds ] = timeString.split(":");
                currentDate.setHours(hours);
                currentDate.setMinutes(minutes);
                currentDate.setSeconds(seconds);
                return currentDate;
        }
        
        const formatTime = convertTimeToDate(start_time)  // method 1 start_time : Fri Dec 27 2024 09:00:00 GMT+0530 (India Standard Time)
        
        start_date = 11-Dec-2024
        new Date(start_date)   
        
        
        const [time, setTime] = useState("2:00 PM");
    const [formattedTime, setFormattedTime] = useState("");

    const handleConvertTime = () => {
        // Parse the input time and format it
        const parsedDate = parse(time, "h:mm a", new Date());
        const formatted = format(parsedDate, "EEE MMM dd yyyy HH:mm:ss 'GMT'xxx (zzzz)");
        setFormattedTime(formatted);
    };

Image upload with preview

import React, { useState } from 'react';
import { Button, Form, Image } from 'react-bootstrap';

const FileUploadWithPreview = () => {
  const [selectedFile, setSelectedFile] = useState(null);
  const [preview, setPreview] = useState(null);

  const handleFileChange = (event) => {
    const file = event.target.files[0];

    if (file) {
      setSelectedFile(file);
      const objectUrl = URL.createObjectURL(file); // Create object URL for preview
      setPreview(objectUrl);
    }
  };

  const handleRemovePreview = () => {
    setSelectedFile(null);
    setPreview(null);
  };

  return (
    <div>
      <Form>
        <Form.Group controlId="fileUpload">
          <Form.Label>Upload File</Form.Label>
          <Form.Control
            type="file"
            onChange={handleFileChange}
            accept="image/*" // Only accept images
          />
        </Form.Group>
      </Form>

      {preview && (
        <div className="mt-3">
          <h5>Preview:</h5>
          <Image
            src={preview}
            alt="Preview"
            style={{ width: '200px', height: 'auto' }}
            thumbnail
          />
          <Button variant="danger" className="mt-2" onClick={handleRemovePreview}>
            Remove Preview
          </Button>
        </div>
      )}
    </div>
  );
};

export default FileUploadWithPreview;

Search

import React, { useState } from "react";

const objectiveLevels = [
  { id: 1, value: "Organization" },
  { id: 2, value: "Organization Unit" },
  { id: 3, value: "Business Unit" },
  { id: 4, value: "Department" },
  { id: 5, value: "Position" },
  { id: 6, value: "Personal" },
];

const ObjectiveSearchQuery = () => {
  const [searchQuery, setSearchQuery] = useState("");

  // Filter the objectiveLevels based on searchQuery input
  const filteredObjectives = objectiveLevels.filter((item) =>
    item.value.toLowerCase().includes(searchQuery.toLowerCase())
  );

  return (
    <div className="p-4">
      <input
        type="text"
        placeholder="Search..."
        className="border p-2 rounded w-full"
        value={searchQuery}
        onChange={(e) => setSearchQuery(e.target.value)}
      />
      <ul className="mt-4">
        {filteredObjectives.length > 0 ? (
          filteredObjectives.map((item) => (
            <li key={item.id} className="p-2 border-b">
              {item.value}
            </li>
          ))
        ) : (
          <li className="p-2 text-gray-500">No results found</li>
        )}
      </ul>
    </div>
  );
};

export default ObjectiveSearchQuery;
    

Number input and e.prevent

        onChange={(e) => {
          const numValue = e.target.value.replace(/\D/g, "")
          handleCurrencyParamsChanges('amount2', numValue ? parseInt(numValue) : '', item.field_name)}
        }


        //stopping a form from submitting or preventing a link from navigating
        e.preventDefault()

        //triggering handlers on parent elements
        e.stopPropagation()

        //e.key (for Keyboard Events)
        if (e.key === "Enter") {
          console.log("Enter key pressed!");
        }
    

React Router (Passing Data via State)

//PageOne.js
        import React from "react";
        import { useNavigate } from "react-router-dom";

        const PageOne = () => {
            const navigate = useNavigate();

            const handleNavigate = () => {
                navigate("/page-two", { state: { message: "Hello from Page One!" } });
            };

            return <button onClick={handleNavigate}>Go to Page Two</button>;
        };

        export default PageOne;


        //PageTwo.js
        import React from "react";
        import { useLocation } from "react-router-dom";

        const PageTwo = () => {
            const location = useLocation();
            const { message } = location.state || {};

            return <p>Message: {message}</p>;
        };

        export default PageTwo;     

Props (Passing Data)

<img src={editIcon} onClick={() => handleNewSubtaskChange(data.sub_task_id)}/>
---
const handleNewSubtaskChange = (subTaskId) =>{
      CreateSubtask(true); ///-- Edit
      setShowNewFormPopup(true);
      setPassDataToSubTask({
        task_id: viewTaskId,
        project_id: projectId,
        stage_id: stageId,
        edit_id: subTaskId
      });
    }

---
<div className={`CreatePopupDsn ${showNewFormPopup ? 'show' : ''}`}>
      <button type="button" className="popup-close btn btn-primary" 
        onClick={handleShowNewFormPopup}
      ></button>
      <TaskCreateSubTask passDataToSubTask={passDataToSubTask}  />

    </div>
---


    function TaskCreateSubTask({onDataReceived, passDataToSubTask}) {


      useEffect(() => {
        if(passDataToSubTask) {
            console.log("subtaskValue",passDataToSubTask, passDataToSubTask.project_id) 
            setProjectValue(passDataToSubTask.project_id); 
        }
        
    }, [passDataToSubTask]); 

-----
function ChildTask({onDataReceived, viewTaskID}) {
      onDataReceived(false);

-----

 <ChildTask 
              onDataReceived={handleDataFromChild}
              viewTaskID={viewTaskID}

              />


const handleDataFromChild = () => {
    setNewTaskPopupForm(false);
    setViewTaskID(null);
    getProjectData()
  };

Date Filter with Monthly, Weekly, and Daily Views

import React, { useState, useEffect } from 'react';
import DatePicker from 'react-datepicker';
import 'react-datepicker/dist/react-datepicker.css';
import { format, addDays, subDays, addMonths, subMonths, startOfMonth, endOfMonth } from 'date-fns';
import { Dropdown } from "react-bootstrap";

const App = () => {  
  const [dateRangePicker, setDateRangePicker] = useState('Monthly');
  const [startDatePicker, setStartDatePicker] = useState(startOfMonth(new Date()));
  const [endDatePicker, setEndDatePicker] = useState(endOfMonth(new Date()));

  const handlePrev = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => subDays(prev, 1));
      setEndDatePicker(prev => subDays(prev, 1));
    } else if (dateRangePicker === "Week") {
      setStartDatePicker(prev => subDays(prev, 7));
      setEndDatePicker(prev => subDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(subMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(subMonths(prev, 1)));
    }
  };

  const handleNext = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => addDays(prev, 1));
      setEndDatePicker(prev => addDays(prev, 1));
    } else if (dateRangePicker === "Week") {
      setStartDatePicker(prev => addDays(prev, 7));
      setEndDatePicker(prev => addDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(addMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(addMonths(prev, 1)));
    }
  };

  const handleDateChange = dateOrDates => {
    if (dateRangePicker === "Monthly") {
      setStartDatePicker(startOfMonth(dateOrDates));
      setEndDatePicker(endOfMonth(dateOrDates));
    } else if (Array.isArray(dateOrDates)) {
      const [start, end] = dateOrDates;
      setStartDatePicker(start);
      setEndDatePicker(end);
    } else {
      setStartDatePicker(dateOrDates);
      setEndDatePicker(addDays(dateOrDates, 1));
    }
  };

  const handleDateRange = (e, dateRangeId) => {
    setDateRangePicker(dateRangeId);
    if (dateRangeId === "Day") {
      setStartDatePicker(new Date());
      setEndDatePicker(addDays(new Date(), 1));
    } else if (dateRangeId === "Week") {
      const today = new Date();
      const startDate = subDays(today, today.getDay());
      const endDate = addDays(startDate, 6);
      setStartDatePicker(startDate);
      setEndDatePicker(endDate);
    } else if (dateRangeId === "Monthly") {
      setStartDatePicker(startOfMonth(new Date()));
      setEndDatePicker(endOfMonth(new Date()));
    }
  };

  return (
    <div>
      
      <div className='d-flex align-items-center justify-content-center'>
        <div className={`d-flex align-items-center justify-content-center gap-10 ${dateRangePicker === "Monthly" ? "month-picker" : ''}`}>
          <button className='left-arrow' onClick={handlePrev}></button>
          {dateRangePicker === "Monthly" && <span>{format(startDatePicker, 'MMM yyyy')}</span>}
          <DatePicker
            selected={startDatePicker}
            onChange={handleDateChange}
            startDate={startDatePicker}
            endDate={dateRangePicker === "Week" || dateRangePicker === "Monthly" ? endDatePicker : ''}
            selectsRange={dateRangePicker === "Week"}
            dateFormat={dateRangePicker === "Week" ? "dd-MM-yyyy" : dateRangePicker === "Monthly" ? "MMM-yyyy" : "dd-MMM-yyyy"}
            showMonthYearPicker={dateRangePicker === "Monthly"}
          />
          <button className='right-arrow' onClick={handleNext}></button>
          <Dropdown className="sortDsn borRight">
            <Dropdown.Toggle id="dropdown-basic" className="fz-15px py-0">
              {dateRangePicker}
            </Dropdown.Toggle>
            <Dropdown.Menu>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Monthly')}>Monthly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Week')}>Week</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Day')}>Day</Dropdown.Item>
            </Dropdown.Menu>
          </Dropdown>
          {startDatePicker ? format(startDatePicker, "yyyy-MM-dd") : ""} to {endDatePicker ? format(endDatePicker, "yyyy-MM-dd") : ""}
        </div>
      </div>
    </div>
  );
};

export default App;

Added Year and Quarterly

import React, { useState } from 'react';
import DatePicker from 'react-datepicker';
import 'react-datepicker/dist/react-datepicker.css';
import { format, addDays, subDays, addMonths, subMonths, startOfMonth, endOfMonth, startOfYear, endOfYear, addYears, subYears, startOfQuarter, endOfQuarter } from 'date-fns';
import { Dropdown } from "react-bootstrap";

const Records = () => {
  const [dateRangePicker, setDateRangePicker] = useState('Monthly');
  const [startDatePicker, setStartDatePicker] = useState(startOfMonth(new Date()));
  const [endDatePicker, setEndDatePicker] = useState(endOfMonth(new Date()));

  const handlePrev = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => subDays(prev, 1));
      setEndDatePicker(prev => subDays(prev, 1));
    } else if (dateRangePicker === "Week") {
      setStartDatePicker(prev => subDays(prev, 7));
      setEndDatePicker(prev => subDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(subMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(subMonths(prev, 1)));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(prev => startOfYear(subYears(prev, 1)));
      setEndDatePicker(prev => endOfYear(subYears(prev, 1)));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(prev => startOfQuarter(subMonths(prev, 3)));
      setEndDatePicker(prev => endOfQuarter(subMonths(prev, 3)));
    }
  };

  const handleNext = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => addDays(prev, 1));
      setEndDatePicker(prev => addDays(prev, 1));
    } else if (dateRangePicker === "Week") {
      setStartDatePicker(prev => addDays(prev, 7));
      setEndDatePicker(prev => addDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(addMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(addMonths(prev, 1)));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(prev => startOfYear(addYears(prev, 1)));
      setEndDatePicker(prev => endOfYear(addYears(prev, 1)));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(prev => startOfQuarter(addMonths(prev, 3)));
      setEndDatePicker(prev => endOfQuarter(addMonths(prev, 3)));
    }
  };

  const handleDateChange = dateOrDates => {
    if (dateRangePicker === "Monthly") {
      setStartDatePicker(startOfMonth(dateOrDates));
      setEndDatePicker(endOfMonth(dateOrDates));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(startOfYear(dateOrDates));
      setEndDatePicker(endOfYear(dateOrDates));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(startOfQuarter(dateOrDates));
      setEndDatePicker(endOfQuarter(dateOrDates));
    } else if (Array.isArray(dateOrDates)) {
      const [start, end] = dateOrDates;
      setStartDatePicker(start);
      setEndDatePicker(end);
    } else {
      setStartDatePicker(dateOrDates);
      setEndDatePicker(addDays(dateOrDates, 1));
    }
  };

  const handleDateRange = (e, dateRangeId) => {
    setDateRangePicker(dateRangeId);
    const today = new Date();
    if (dateRangeId === "Day") {
      setStartDatePicker(today);
      setEndDatePicker(addDays(today, 1));
    } else if (dateRangeId === "Week") {
      const startDate = subDays(today, today.getDay());
      const endDate = addDays(startDate, 6);
      setStartDatePicker(startDate);
      setEndDatePicker(endDate);
    } else if (dateRangeId === "Monthly") {
      setStartDatePicker(startOfMonth(today));
      setEndDatePicker(endOfMonth(today));
    } else if (dateRangeId === "Yearly") {
      setStartDatePicker(startOfYear(today));
      setEndDatePicker(endOfYear(today));
    } else if (dateRangeId === "Quarterly") {
      setStartDatePicker(startOfQuarter(today));
      setEndDatePicker(endOfQuarter(today));
    }
  };

  return (
    <div>
      <br /><br /><br />
      <div className='d-flex align-items-center justify-content-center'>
        <div className={`d-flex align-items-center justify-content-center gap-10 ${dateRangePicker === "Monthly" ? "month-picker" : ''}`}>
          <button className='left-arrow' onClick={handlePrev}></button>
          {dateRangePicker === "Monthly" && <span>{format(startDatePicker, 'MMM yyyy')}</span>}
          {dateRangePicker === "Yearly" && <span>{format(startDatePicker, 'yyyy')}</span>}
          {dateRangePicker === "Quarterly" && <span>{`Q${Math.ceil((startDatePicker.getMonth() + 1) / 3)} ${format(startDatePicker, 'yyyy')}`}</span>}
          <DatePicker
            selected={startDatePicker}
            onChange={handleDateChange}
            startDate={startDatePicker}
            endDate={dateRangePicker === "Week" || dateRangePicker === "Monthly" || dateRangePicker === "Yearly" || dateRangePicker === "Quarterly" ? endDatePicker : ''}
            selectsRange={dateRangePicker === "Week"}
            dateFormat={dateRangePicker === "Yearly" ? "yyyy" : dateRangePicker === "Monthly" ? "MMM-yyyy" : dateRangePicker === "Quarterly" ? "MMM-yyyy" : "dd-MMM-yyyy"}
            showMonthYearPicker={dateRangePicker === "Monthly" || dateRangePicker === "Quarterly"}
            showYearPicker={dateRangePicker === "Yearly"}
          />
          <button className='right-arrow' onClick={handleNext}></button>
          <Dropdown className="sortDsn borRight">
            <Dropdown.Toggle id="dropdown-basic" className="fz-15px py-0">
              {dateRangePicker}
            </Dropdown.Toggle>
            <Dropdown.Menu>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Monthly')}>Monthly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Week')}>Week</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Day')}>Day</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Yearly')}>Yearly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Quarterly')}>Quarterly</Dropdown.Item>
            </Dropdown.Menu>
          </Dropdown>
          {startDatePicker ? format(startDatePicker, "yyyy-MM-dd") : ""} to {endDatePicker ? format(endDatePicker, "yyyy-MM-dd") : ""}
        </div>
      </div>
    </div>
  );
};

export default Records;

Added Year and Quarterly

import React, { useState, useEffect } from 'react';
import DatePicker from 'react-datepicker';
import 'react-datepicker/dist/react-datepicker.css';
import { format, addDays, subDays, addMonths, subMonths, startOfMonth, endOfMonth, startOfYear, endOfYear, addYears, subYears, startOfQuarter, endOfQuarter } from 'date-fns';
import { Dropdown } from "react-bootstrap";

const Records = () => {
  const [dateRangePicker, setDateRangePicker] = useState('Yearly');
  const [startDatePicker, setStartDatePicker] = useState(startOfMonth(new Date()));
  const [endDatePicker, setEndDatePicker] = useState(endOfMonth(new Date()));
  const [selectedYear, setSelectedYear]= useState(new Date())

  const [dateRangeLimits, setDateRangeLimits]= useState({
    start_date : '',
    end_date: ''
  })

  const handlePrev = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => subDays(prev, 1));
      setEndDatePicker(prev => subDays(prev, 1));
    } else if (dateRangePicker === "Custom") {
      setStartDatePicker(prev => subDays(prev, 7));
      setEndDatePicker(prev => subDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(subMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(subMonths(prev, 1)));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(prev => startOfYear(subYears(prev, 1)));
      setEndDatePicker(prev => endOfYear(subYears(prev, 1)));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(prev => startOfQuarter(subMonths(prev, 3)));
      setEndDatePicker(prev => endOfQuarter(subMonths(prev, 3)));
    }
  };

  const handleNext = () => {
    if (dateRangePicker === "Day") {
      setStartDatePicker(prev => addDays(prev, 1));
      setEndDatePicker(prev => addDays(prev, 1));
    } else if (dateRangePicker === "Custom") {
      setStartDatePicker(prev => addDays(prev, 7));
      setEndDatePicker(prev => addDays(prev, 7));
    } else if (dateRangePicker === "Monthly") {
      setStartDatePicker(prev => startOfMonth(addMonths(prev, 1)));
      setEndDatePicker(prev => endOfMonth(addMonths(prev, 1)));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(prev => startOfYear(addYears(prev, 1)));
      setEndDatePicker(prev => endOfYear(addYears(prev, 1)));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(prev => startOfQuarter(addMonths(prev, 3)));
      setEndDatePicker(prev => endOfQuarter(addMonths(prev, 3)));
    }
  };

  const handleDateChange = dateOrDates => {
    if (dateRangePicker === "Monthly") {
      setStartDatePicker(startOfMonth(dateOrDates));
      setEndDatePicker(endOfMonth(dateOrDates));
    } else if (dateRangePicker === "Yearly") {
      setStartDatePicker(startOfYear(dateOrDates));
      setEndDatePicker(endOfYear(dateOrDates));
    } else if (dateRangePicker === "Quarterly") {
      setStartDatePicker(startOfQuarter(dateOrDates));
      setEndDatePicker(endOfQuarter(dateOrDates));
    } else if (Array.isArray(dateOrDates)) {
      const [start, end] = dateOrDates;
      setStartDatePicker(start);
      setEndDatePicker(end);
    } else {
      setStartDatePicker(dateOrDates);
      setEndDatePicker(addDays(dateOrDates, 1));
    }
  };

  const handleDateRange = (e, dateRangeId) => {
    setDateRangePicker(dateRangeId);
    const today = new Date(selectedYear);
    if (dateRangeId === "Day") {
      setStartDatePicker(today);
      setEndDatePicker(addDays(today, 1));
    } else if (dateRangeId === "Custom") {
      const startDate = subDays(today, today.getDay());
      const endDate = addDays(startDate, 6);
      setStartDatePicker(startDate);
      setEndDatePicker(endDate);
    } else if (dateRangeId === "Monthly") {
      setStartDatePicker(startOfMonth(today));
      setEndDatePicker(endOfMonth(today));
    } else if (dateRangeId === "Yearly") {
      setStartDatePicker(startOfYear(today));
      setEndDatePicker(endOfYear(today));
    } else if (dateRangeId === "Quarterly") {
      setStartDatePicker(startOfQuarter(today));
      setEndDatePicker(endOfQuarter(today));
    }
  };

  const handleYearChange = (date) => {    
    setSelectedYear(date);    
  };

  useEffect(()=>{
    const end = new Date(selectedYear.getFullYear(), 11, 31);
    setDateRangeLimits({
      start_date : new Date(selectedYear.getFullYear(), 0, 1), 
      end_date: end, 
    });
    setDateRangePicker("Yearly")

    setStartDatePicker(startOfYear(selectedYear));
      setEndDatePicker(endOfYear(selectedYear));

  },[selectedYear])

  return (
    <div>
      <div className='d-flex align-items-center justify-content-center'>
        <div className={`d-flex align-items-center justify-content-center gap-10 ${dateRangePicker === "Monthly" ? "month-picker" : ''}`}>
          <button className='left-arrow' onClick={handlePrev}><</button>
          <DatePicker
            selected={startDatePicker}
            onChange={handleDateChange}
            startDate={startDatePicker}
            endDate={dateRangePicker === "Custom" || dateRangePicker === "Monthly" || dateRangePicker === "Yearly" || dateRangePicker === "Quarterly" ? endDatePicker : ''}
            selectsRange={dateRangePicker === "Custom"}
            dateFormat={dateRangePicker === "Yearly" ? "yyyy" : dateRangePicker === "Monthly" ? "MMM-yyyy" : dateRangePicker === "Quarterly" ? "yyyy, QQQ" : "dd-MMM-yyyy"}
            showMonthYearPicker={dateRangePicker === "Monthly"}            
            showQuarterYearPicker={dateRangePicker === "Quarterly"}
            disabled={dateRangePicker === "Yearly"}
            minDate={dateRangeLimits.start_date}
            maxDate={dateRangeLimits.end_date}
          />
          <button className='right-arrow' onClick={handleNext}>></button>
          <Dropdown className="sortDsn borRight">
            <Dropdown.Toggle id="dropdown-basic" className="fz-15px py-0">
              {dateRangePicker}
            </Dropdown.Toggle>
            <Dropdown.Menu>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Yearly')}>Yearly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Quarterly')}>Quarterly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Monthly')}>Monthly</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Custom')}>Custom</Dropdown.Item>
              <Dropdown.Item onClick={(e) => handleDateRange(e, 'Day')}>Day</Dropdown.Item>             
              
            </Dropdown.Menu>
          </Dropdown>
          <DatePicker
            selected={selectedYear}
            onChange={handleYearChange}            
            showYearPicker
            dateFormat="yyyy"
            dropdownMode="select"            
          />
          {selectedYear? format(selectedYear, "yyyy") : ""} ----
          {startDatePicker ? format(startDatePicker, "yyyy-MM-dd") : ""} to {endDatePicker ? format(endDatePicker, "yyyy-MM-dd") : ""}
        </div>
      </div>
    </div>
  );
};

export default Records;

Json Data Filter

import React, { useEffect, useState, useMemo } from "react";
import DatePicker from "react-datepicker";
import "react-datepicker/dist/react-datepicker.css";


const budgetData = [ 
    { no: 1, name: "Coffee", date: "2025-01-15T18:30:00.000Z", amount: 150, category: 1 },
    { no: 2, name: "Groceries", date: "2025-01-16T18:30:00.000Z", amount: 1200, category: 1 },
    { no: 3, name: "Movie Ticket", date: "2025-01-17T18:30:00.000Z", amount: 400, category: 3, sub_budget: [
        { sub_no: 1, name: "Parking", amount: 50 },
        { sub_no: 2, name: "Ticket", amount: 250, sub_budget: [
            { sub_sub_no: 1, name: "Premium Seat", amount: 100 }
        ] },
        { sub_no: 3, name: "Popcorn", amount: 100 }
    ] },
    { no: 4, name: "Gym Membership", date: "2025-01-18T18:30:00.000Z", amount: 2000, category: 3 },
    { no: 5, name: "Dinner", date: "2025-01-19T18:30:00.000Z", amount: 850, category: 1 },
    { no: 6, name: "Electricity Bill", date: "2025-01-20T18:30:00.000Z", amount: 3000, category: 2 },
    { no: 7, name: "Internet Bill", date: "2025-01-21T18:30:00.000Z", amount: 1200, category: 2 },
    { no: 8, name: "Books", date: "2025-01-22T18:30:00.000Z", amount: 750, category: 3 },
    { no: 9, name: "Taxi", date: "2025-01-23T18:30:00.000Z", amount: 500, category: 4 },
    { no: 10, name: "Shopping", date: "2025-01-24T18:30:00.000Z", amount: 2500, category: 3 },
    { no: 11, name: "Subscription", date: "2025-01-25T18:30:00.000Z", amount: 999, category: 3 },
    { no: 12, name: "Lunch", date: "2025-01-26T18:30:00.000Z", amount: 600, category: 1 },
    { no: 13, name: "Water Bill", date: "2025-01-27T18:30:00.000Z", amount: 700, category: 2 },
    { no: 14, name: "Concert Ticket", date: "2025-01-28T18:30:00.000Z", amount: 1800, category: 3 },
    { no: 15, name: "Gas", date: "2025-01-29T18:30:00.000Z", amount: 2200, category: 4 }
];

const BudgetFilter = () => {
    const [startDate, setStartDate] = useState(null);
    const [endDate, setEndDate] = useState(null);
    const [groupType, setGroupType] = useState("category");
    const [filterData, setFilterData] = useState({});

    // Memoize filteredData to prevent recalculating on every render
    const filteredData = useMemo(() => {
        return budgetData.filter(item => {
            const itemDate = new Date(item.date);
            return (
                (!startDate || itemDate >= startDate) &&
                (!endDate || itemDate <= endDate)
            );
        });
    }, [startDate, endDate, budgetData]);

    // Memoize groupedData to prevent recalculating on every render
    const groupedData = useMemo(() => {
        return filteredData.reduce((acc, item) => {
            //const groupKey = item[groupType];
            const groupKey = groupType === "date" ? new Date(item.date).toISOString().split("T")[0] : item[groupType];
            
            if (!acc[groupKey]) {
                acc[groupKey] = { group: groupKey, group_data: [] };
            }
            acc[groupKey].group_data.push(item);
            return acc;
        }, {});
    }, [filteredData, groupType]);

    useEffect(() => {
        setFilterData(groupedData);
    }, [groupedData]);

    const renderSubBudget = (subBudget, level = 1) => {
        return (
            <ul style={{ paddingLeft: `${level * 20}px` }}>
                {subBudget.map(sub => (
                    <li key={sub.sub_no || sub.sub_sub_no}>
                        {sub.name} - {sub.amount}
                        {sub.sub_budget && renderSubBudget(sub.sub_budget, level + 1)}
                    </li>
                ))}
            </ul>
        );
    };

    return (
        <div>
            <h2>Budget Data Filter</h2>
            <label>Start Date:</label>
            <DatePicker
                selected={startDate}
                onChange={date => setStartDate(date)}
                dateFormat="yyyy-MM-dd"
            />
            
            <label>End Date:</label>
            <DatePicker
                selected={endDate}
                onChange={date => setEndDate(date)}
                dateFormat="yyyy-MM-dd"
            />
            
            <label>Group By:</label>
            <select value={groupType} onChange={(e) => setGroupType(e.target.value)}>
                <option value="amount">Amount</option>
                <option value="category">Category</option>
                <option value="date">Date</option>
            </select>

            <h3>Filtered Results</h3>
            {Object.values(filterData).map(group => (
                <div key={group.group}>
                    <h4>{groupType.charAt(0).toUpperCase() + groupType.slice(1)} {group.group}</h4>
                    <ul>
                        {group.group_data.map(item => (
                            <li key={item.no}>
                                {item.name} - {item.amount} ({new Date(item.date).toLocaleDateString()})
                                {item.sub_budget && renderSubBudget(item.sub_budget)}
                            </li>
                        ))}
                    </ul>
                </div>
            ))}

        </div>
    );
};

export default BudgetFilter;

Context API

What is useContext in React?

useContext is a React Hook that lets you read data from a Context inside any component.

A Context is a way to share data (like theme, user login info, language, etc.) across many components, without passing props manually through every level.

Purpose of useContext

It makes your code cleaner, shorter, and easier to manage.

To make global values (like settings, user data) easily available anywhere in the app..

To avoid "prop drilling" — meaning you don't have to pass the same data from parent → child → grandchild → great-grandchild, etc.

//App.js
    import React from "react";
    import DataProvider from "./Components/DataContext";
    import ComponentOne from "./Components/ComponentOne";
    import ComponentTwo from "./Components/ComponentTwo";
    
    const App = () => {
        return (
            <DataProvider>
                <ComponentOne />
                <ComponentTwo />
            </DataProvider>
        );
    };
    
    export default App;

    //DataContext.js
    import React, { createContext, useState } from "react";

    export const DataContext = createContext();

    const DataProvider = ({ children }) => {
        const [data, setData] = useState("Global Data");

        const [newdata, setNewData] = useState("Global new Data");

        return (
            <DataContext.Provider value={{ data, setData,  newdata, setNewData }}>
                {children}
            </DataContext.Provider>
        );
    };

    export default DataProvider;


    //ComponentOne.js
    import React, { useContext, useState } from "react";
    import { DataContext } from "./DataContext";

    const ComponentOne = () => {
        const { setData, setNewData } = useContext(DataContext);

        const [userName, setUserName] =useState('')

        const handleNamechange = () => {
            setNewData(userName);
        }

        return (
            <>
                <button onClick={() => setData("Updated Data from Component One")}>
                    Update Data
                </button>

                <input type="text" value={userName} placeholder="Enter your Name" onChange={(e) => setUserName(e.target.value)} />

                <button onClick={() => handleNamechange()}>
                    Update Data
                </button>
            </>
        );
    };

    export default ComponentOne;

    //ComponentTwo.js
    import React, { useContext } from "react";
    import { DataContext } from "./DataContext";

    const ComponentTwo = () => {
        const { data } = useContext(DataContext);
        const { newdata } = useContext(DataContext);

        return <p>Hi {newdata}, Data from Context: {data}</p>;
    };

    export default ComponentTwo;

Redux

Redux is for JavaScript applications

Redux is not tied to React

Can be used with React, Angular, Vue or even vanilla JavaScript

Redux is a library for JavaScript applications

Redux is State Container

Redux is Prectable State Container for JavaScript app

Redux Redux toolkit
Not much organised organised
Lot of repetition CreateSlice (cleaner and smaller)
Manual Configration Auto Configration
Config redux devtool extension Auto support
manually handle and change state immutably
(immutable state means always written a new state)
immer.js support(auto change code)
Stoer too complication -
Class based implementation function based with typescript and support of hooks
npm install @reduxjs/toolkit react-redux



    // src/features/counter/counterSlice.js
    import { createSlice } from '@reduxjs/toolkit';
    
    const initialState = {
     value: 0
    };
    
    const counterSlice = createSlice({
     name: 'counter',
     initialState,
     reducers: {
        increment: (state) => {
         state.value += 1;
        },
        decrement: (state) => {
         state.value -= 1;
        },
        reset: (state) => {
         state.value = 0;
        },
        incrementByAmount: (state, action) => {
         state.value += action.payload;
        },
     },
    });
    
    export const { increment, decrement, reset, incrementByAmount } = counterSlice.actions;
    
    export default counterSlice.reducer;



    // src/app/store.js
import { configureStore } from '@reduxjs/toolkit';
import counterReducer from '../features/counter/counterSlice';

export const store = configureStore({
reducer: {
counter: counterReducer,
},
});


// src/index.js
import React from 'react';
import ReactDOM from 'react-dom/client';
import App from './App';
import { Provider } from 'react-redux';
import { store } from './app/store';

const root = ReactDOM.createRoot(document.getElementById('root'));
root.render(
<Provider store={store}>
<App />
</Provider>
);



// src/features/counter/Counter.js
import React, { useState } from 'react';
import { useSelector, useDispatch } from 'react-redux';
import {
increment,
decrement,
reset,
incrementByAmount,
} from './counterSlice';

const Counter = () => {
const count = useSelector((state) => state.counter.value);
const dispatch = useDispatch();
const [amount, setAmount] = useState(0);

return (
<div>
 <h2>Count: {count}</h2>
 <button onClick={() => dispatch(increment())}>+1</button>
 <button onClick={() => dispatch(decrement())}>-1</button>
 <button onClick={() => dispatch(reset())}>Reset</button>

 <div>
    <input
     type="number"
     value={amount}
     onChange={(e) => setAmount(Number(e.target.value))}
    />
    <button onClick={() => dispatch(incrementByAmount(amount))}>
     Increment by Amount
    </button>
 </div>
</div>
);
};

export default Counter;