diff --git a/client/react/src/forms/NewLightForm.js b/client/react/src/forms/NewLightForm.js
new file mode 100644
index 0000000..c2dbb9f
--- /dev/null
+++ b/client/react/src/forms/NewLightForm.js
@@ -0,0 +1,140 @@
+import React, { useState, useEffect } from 'react';
+import Modal from '@mui/material/Modal';
+import TextField from '@mui/material/TextField';
+import Box from '@mui/material/Box';
+import IconButton from '@mui/material/IconButton';
+import ButtonGroup from '@mui/material/ButtonGroup';
+import CheckSharpIcon from '@mui/icons-material/CheckSharp';
+import CloseSharpIcon from '@mui/icons-material/CloseSharp';
+import Autocomplete from '@mui/material/Autocomplete';
+import TungstenSharpIcon from '@mui/icons-material/TungstenSharp';
+
+
+const NewLightForm = ({ isOpen, onRequestClose }) => {
+
+ const [name, setName] = useState('');
+ const [system, setSystem] = useState(null);
+ const [cost, setCost] = useState(0);
+
+ const [allSystems, setAllSystems] = useState([]);
+
+ const [submitted, setSubmitted] = useState(false);
+
+ useEffect(() => {
+ fetch('http://127.0.0.1:5000/system')
+ .then((response) => response.json())
+ .then((data) => setAllSystems(data))
+ .catch((error) => console.error('Error fetching all system data:', error));
+
+ }, []);
+
+ useEffect(() => {
+ if (submitted) {
+ const requestOptions = {
+ method: 'POST',
+ headers: { 'Content-Type': 'application/json' },
+ body: JSON.stringify({name: name, cost: cost, system_id: system.id })
+ };
+ fetch('http://127.0.0.1:5000/light', requestOptions)
+ .then(response => response.json())
+ .then(data => {
+ // handle the response data if needed
+ // maybe update some state based on the response
+ console.log(data);
+ })
+ .catch(error => console.error('Error posting plants data:', error));
+ clearForm();
+ onRequestClose();
+ }
+ }, [submitted, name, cost, system, onRequestClose]);
+
+ const handleSubmit = (event) => {
+ event.preventDefault();
+ setSubmitted(true); // Update submitted state
+ };
+
+ const handleCancel = () => {
+ clearForm();
+ onRequestClose();
+ };
+
+ const clearForm = () => {
+ setName('');
+ setCost(0);
+ setSystem(null);
+ setSubmitted(false);
+ };
+
+ return (
+
+
+
+
+
+ );
+};
+
+export default NewLightForm;
diff --git a/client/react/src/forms/NewSystemForm.js b/client/react/src/forms/NewSystemForm.js
index 5f5c8f7..c363aa6 100644
--- a/client/react/src/forms/NewSystemForm.js
+++ b/client/react/src/forms/NewSystemForm.js
@@ -13,7 +13,11 @@ const NewSystemForm = ({ isOpen, onRequestClose }) => {
const [name, setName] = useState('');
const [humidity, setHumidity] = useState(0);
const [temperature, setTempurature] = useState(0);
+ const [duration, setDuration] = useState(0);
+ const [distance, setDistance] = useState(0);
+
const [allSystems, setAllSystems] = useState([]);
+
const [submitted, setSubmitted] = useState(false);
useEffect(() => {
@@ -31,7 +35,7 @@ const NewSystemForm = ({ isOpen, onRequestClose }) => {
const requestOptions = {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
- body: JSON.stringify({ name: name, humidity: humidity, temperature: temperature })
+ body: JSON.stringify({ name: name, humidity: humidity, temperature: temperature, distance: distance, duration: duration })
};
fetch('http://127.0.0.1:5000/system', requestOptions)
.then(response => response.json())
@@ -44,7 +48,7 @@ const NewSystemForm = ({ isOpen, onRequestClose }) => {
clearForm();
onRequestClose();
}
- }, [submitted, name, temperature, humidity, onRequestClose]);
+ }, [submitted, name, temperature, humidity, distance, duration, onRequestClose]);
const handleSubmit = (event) => {
event.preventDefault();
@@ -60,6 +64,8 @@ const NewSystemForm = ({ isOpen, onRequestClose }) => {
setName('');
setTempurature(0);
setHumidity(0);
+ setDistance(0);
+ setDuration(0);
setSubmitted(false);
};
@@ -120,6 +126,26 @@ const NewSystemForm = ({ isOpen, onRequestClose }) => {
onChange={(event) => setTempurature(event.target.value)}
variant="standard"
/>
+ setDuration(event.target.value)}
+ variant="standard"
+ />
+ setDistance(event.target.value)}
+ variant="standard"
+ />
diff --git a/client/react/src/pages/Home.js b/client/react/src/pages/Home.js
index 182c082..9c5375e 100644
--- a/client/react/src/pages/Home.js
+++ b/client/react/src/pages/Home.js
@@ -15,6 +15,9 @@ import Box from '@mui/material/Box';
import CloseSharpIcon from '@mui/icons-material/CloseSharp';
import VisibilitySharpIcon from '@mui/icons-material/VisibilitySharp';
import ReportGmailerrorredSharpIcon from '@mui/icons-material/ReportGmailerrorredSharp';
+import NewLightForm from '../forms/NewLightForm';
+import TungstenSharpIcon from '@mui/icons-material/TungstenSharp';
+
const Home = () => {
// Navigation
@@ -30,6 +33,7 @@ const Home = () => {
const [isNewPlantFormOpen, setIsNewPlantFormOpen] = useState(false);
const [isNewSystemFormOpen, setIsNewSystemFormOpen] = useState(false);
const [isNewGenusFormOpen, setIsNewGenusFormOpen] = useState(false);
+ const [isNewLightFormOpen, setIsNewLightFormOpen] = useState(false);
useEffect(() => {
// Fetch plant data from the server
@@ -76,6 +80,9 @@ const Home = () => {
setIsNewGenusFormOpen(true)}>
+ setIsNewLightFormOpen(true)}>
+
+
setIsCreateButtonsOpen(false)}>
@@ -108,6 +115,10 @@ const Home = () => {
isOpen={isNewGenusFormOpen}
onRequestClose={() => setIsNewGenusFormOpen(false)}
/>
+ setIsNewLightFormOpen(false)}
+ />
>
);
diff --git a/server/app.py b/server/app.py
index ff0dc47..2f015be 100644
--- a/server/app.py
+++ b/server/app.py
@@ -16,7 +16,7 @@
# Local application imports
from models.plant import Plant, Genus
-from models.system import System
+from models.system import System, Light
# Load database configuration from JSON file
with open("db.json", encoding="utf-8") as json_data_file:
@@ -32,6 +32,7 @@
port=db_config["port"],
)
engine = create_engine(url)
+
# Base.metadata.drop_all(engine)
# Base.metadata.create_all(engine)
@@ -173,6 +174,8 @@ def create_system():
name=new_system_json["name"],
temperature=new_system_json["temperature"],
humidity=new_system_json["humidity"],
+ duration=new_system_json["duration"],
+ distance=new_system_json["distance"]
)
# Add the new system object to the session
@@ -183,6 +186,44 @@ def create_system():
return jsonify({"message": "System added successfully"}), 201
+@app.route("/light", methods=["GET"])
+def get_light():
+ """
+ Retrieve all lights from the database.
+ """
+ logger.info("Received request to retrieve all lights")
+
+ session = Session()
+ lights = session.query(Light).all()
+ session.close()
+ # Transform lights to JSON format
+ lights_json = [light.to_json() for light in lights]
+ # Return JSON response
+ return jsonify(lights_json)
+
+@app.route("/light", methods=["POST"])
+def create_light():
+ """
+ Create a new light and add it to the database.
+ """
+ logger.info("Attempting to create light")
+
+ new_light_json = request.get_json()
+
+ # Create a new Light object
+ new_light = Light(
+ name=new_light_json["name"],
+ cost=new_light_json["cost"],
+ system_id=new_light_json["system_id"],
+ )
+
+ # Add the new Light object to the session
+ db = Session()
+ db.add(new_light)
+ db.commit()
+ db.close()
+
+ return jsonify({"message": "Light added successfully"}), 201
if __name__ == "__main__":
# Run the Flask app
diff --git a/server/models/system.py b/server/models/system.py
index 5a629c3..b5ef602 100644
--- a/server/models/system.py
+++ b/server/models/system.py
@@ -6,8 +6,8 @@
from typing import List
# Third-party imports
-from sqlalchemy import Column, Integer, String, DateTime
-from sqlalchemy.orm import relationship, Mapped
+from sqlalchemy import Column, Integer, String, DateTime, Boolean, ForeignKey
+from sqlalchemy.orm import relationship, Mapped, mapped_column
from models.plant import Base
@@ -31,9 +31,11 @@ class System(Base):
) # Available plants of this system
# Lighting
- # duration = Column(Integer()) # hours
- # distance = Column(Integer()) # inches
- # light: Mapped["Light"] = relationship(back_populates="plants")
+ duration = Column(Integer(), nullable=False) # hours
+ distance = Column(Integer(), nullable=False) # inches
+ lights: Mapped[List["Light"]] = relationship(
+ "Light", backref="system", passive_deletes=True
+ ) # Available plants of this system
def __repr__(self) -> str:
return f"{self.name}"
@@ -47,24 +49,41 @@ def to_json(self):
"updated_on": self.updated_on,
"humidity": self.humidity,
"temperature": self.temperature,
- # "duration": self.duration,
- # "distance": self.distance
+ "duration": self.duration,
+ "distance": self.distance
}
-# class Light(Base):
-# """Light model."""
+class Light(Base):
+ """Light model."""
+
+ __tablename__ = "light"
-# __tablename__ = "light"
+ id = Column(Integer(), primary_key=True)
+ name = Column(String(100), nullable=False)
+ created_on = Column(DateTime(), default=datetime.now)
+ updated_on = Column(DateTime(), default=datetime.now)
+ cost = Column(Integer())
+ system_id: Mapped[int] = mapped_column(
+ ForeignKey("system.id", ondelete="CASCADE")
+ ) # System this light belongs to
-# id = Column(Integer(), primary_key=True)
-# name = Column(String(100), nullable=False)
-# created_on = Column(DateTime(), default=datetime.now)
-# cost = Column(Integer())
+ # Death Info
+ dead_on = Column(DateTime(), default=None, nullable=True)
+ dead = Column(Boolean, default=False, nullable=False)
-# # Death Info
-# dead_on = Column(DateTime(), default=None, nullable=True)
-# dead = Column(Boolean, default=False, nullable=False)
+ def __repr__(self) -> str:
+ return f"{self.name}"
-# def __repr__(self) -> str:
-# return f"{self.name}"
+ def to_json(self):
+ """Convert to json."""
+ return {
+ "id": self.id,
+ "name": self.name,
+ "cost": self.cost,
+ "created_on": self.created_on,
+ "updated_on": self.updated_on,
+ "system_id": self.system_id,
+ "dead": self.dead,
+ "dead_on": self.dead_on
+ }