I'm trying to return the faculty data with it's corresponding students, professors, subjects and grade, I get this Error 500:
I want postman to return this: to display the faculty that is searched by id and inside the faculty the student with the data of subjects, professor and grade of the student.
{
"id": 1,
"university_id": 1,
"name": "FSHMN",
"Enrolled Students:": [
{
{
"id": "5",
"username": "Student5",
"password": "d123",
"fullname": "Student",
"email": "Student#gmail.com",
"subjects": [
{
"id": 1,
"name": "Programim 1",
"Professor": [
{
"id": 1,
"first name": "Stephen",
"last name": "Hawking",
"Title": "Docen"
}
],
"Grade": [
{
"grade_id": 2,
"mark": 9,
"description": "Very Good"
}
]
},
{
"id": 2,
"name": "Programim 2",
"Professor": [
{
"id": 2,
"first name": "John",
"last name": "VonNeuman",
"Title": "Inordinar"
}
],
"Grade": [
{
"grade_id":1,
"mark": 10,
"description": "Very well Done"
}
]
},
{
"id": 3,
"name": "Calculus",
"Professor": [
{
"id": 3,
"first name": "Albert",
"last name": "Einstein",
"Title": "Ordinar"
}
],
"Grade": [
{
"grade_id": 4,
"mark": 7,
"description": "well"
}
]
},
{
"id": 4,
"name": "Discrete mathematics",
"Professor": [
{
"id": 4,
"first name": "John",
"last name": "Feynman",
"Title": "Rektor"
}
],
"Grade": [
{
"grade_id": 2,
"mark": 8,
"description": " Good"
}
]
}
]
}
]
}
Here are the methods that the GET Request is Calling:
public Faculty getFacultyStudent(int id) throws Exception {
Connection connection = null;
Faculty faculty = new Faculty();
Student student = new Student();
HashMap<String,List<Student>> studentFacultyMap=new HashMap<>();
HashMap<String,Professor> professorHashMap=new HashMap<>();
HashMap<String, List<StudentMark>> studentMarksHashMap=new HashMap<>();
faculty.setStudentList(new ArrayList<>());
Map<String,Subject> subjectMap = new HashMap<>();
try {
connection = new MysqlDbConnectionService().getConnection();
String select = "SELECT f.fid, f.fname, f.university_id, s.user_id, s.username, s.password, s.fullname, s.email, "+
" s.email, subj.id , subj.name , p.professor_id, p.first_name, p.last_name, p.title, g.grade_id, g.mark, g.description" +
" FROM faculty f " +
" INNER JOIN student_faculty sf ON sf.faculty_id=f.fid " +
" INNER JOIN student s ON sf.student_id=s.user_id " +
" INNER JOIN faculty_subject fs ON f.fid = fs.faculty_id " +
" INNER JOIN subject subj ON fs.subject_id = subj.id " +
" INNER JOIN professor_subject ps ON ps.subject_id = subj.id " +
" INNER JOIN professor p ON ps.prof_id = p.professor_id " +
" INNER JOIN student_subject_marks sm ON sm.student_id = s.user_id and sm.subject_id = subj.id" +
" INNER JOIN grade g ON sm.grade_id = g.grade_id " +
"WHERE fid = ?";
PreparedStatement ps = connection.prepareStatement(select);
ps.setInt(1, id);
ResultSet rs = ps.executeQuery();
studentFacultyMap= facultyService.getFacultyStudentMap(id);
professorHashMap=facultyService.getProfessors(id);
studentMarksHashMap=facultyService.getStudentSubjectMarks(id);
while (rs.next()) {
if(faculty.getFid()==0) {
faculty.setFid(rs.getInt("fid"));
faculty.setUniversityid(rs.getInt("university_id"));
faculty.setFname(rs.getString("fname"));
}
String subjectID=rs.getString("id");
Subject subject =null;
if(!subjectMap.containsKey(subjectID)) {
subject = new Subject();
subject.setProfessorList(new ArrayList<>());
subject.setMarkList(new ArrayList<>());
subject.setId(rs.getInt("id"));
subject.setName(rs.getString("name"));
subjectMap.put(subjectID, subject);
subject.getProfessorList().addAll(professorHashMap.values());
subject.getMarkList().addAll((Collection<? extends StudentMark>); studentMarksHashMap.values());
}
else{
subject = subjectMap.get(subjectID);
}
student= (Student) studentFacultyMap.values();
student.getSubjectList().add(subject);
}
} catch (Exception e) {
System.out.println(e + " Retrieve not successful");
}
faculty.getStudentList().add(student);
return faculty;
}
This method calls 3 more methods that generate the student, professor and grade data:
This method gets the student:
private HashMap<String,List<Student>> getFacultyStudentMap(int id){
Connection connection = null;
HashMap<String,List<Student>> studentMap=new HashMap<>();
try {
connection = new MysqlDbConnectionService().getConnection();
String select = "SELECT f.fid, f.fname, f.university_id, s.user_id, s.username, s.password, s.fullname, s.email, " +
" s.email, subj.id , subj.name , p.professor_id, p.first_name, p.last_name, p.title, g.grade_id, g.mark, g.description" +
" FROM faculty f " +
" INNER JOIN student_faculty sf ON sf.faculty_id=f.fid " +
" INNER JOIN student s ON sf.student_id=s.user_id " +
" INNER JOIN faculty_subject fs ON f.fid = fs.faculty_id " +
" INNER JOIN subject subj ON fs.subject_id = subj.id " +
" INNER JOIN professor_subject ps ON ps.subject_id = subj.id " +
" INNER JOIN professor p ON ps.prof_id = p.professor_id " +
" INNER JOIN student_subject_marks sm ON sm.student_id = s.user_id and sm.subject_id = subj.id" +
" INNER JOIN grade g ON sm.grade_id = g.grade_id " +
"WHERE fid = ?";
//
//
PreparedStatement ps = connection.prepareStatement(select);
ps.setInt(1, id);
//
ResultSet rs = ps.executeQuery();
String userID = rs.getString("user_id");
Student student = null;
while (rs.next()) {
if (!studentMap.containsKey(userID)) {
student = new Student();
student.setSubjectList(new ArrayList<>());
student.setId(rs.getString("user_id"));
student.setUsername(rs.getString("username"));
student.setPassword(rs.getString("password"));
student.setFullName(rs.getString("fullname"));
student.setEmail(rs.getString("email"));
studentMap.put(userID, (List<Student>) student);
}
else{
student = (Student) studentMap.get(userID);
}
}
}
catch(Exception e)
{
System.out.println("FacultyStudentMap: " + e);
}
return studentMap;
}
This method gets professor:
private HashMap<String,Professor> getProfessors(int id){
Connection connection = null;
HashMap<String,Professor> professorMap=new HashMap<>();
try{
connection = new MysqlDbConnectionService().getConnection();
String select = "SELECT f.fid, f.fname, f.university_id, s.user_id, s.username, s.password, s.fullname, s.email, "+
" s.email, subj.id , subj.name , p.professor_id, p.first_name, p.last_name, p.title, g.grade_id, g.mark, g.description" +
" FROM faculty f " +
" INNER JOIN student_faculty sf ON sf.faculty_id=f.fid " +
" INNER JOIN student s ON sf.student_id=s.user_id " +
" INNER JOIN faculty_subject fs ON f.fid = fs.faculty_id " +
" INNER JOIN subject subj ON fs.subject_id = subj.id " +
" INNER JOIN professor_subject ps ON ps.subject_id = subj.id " +
" INNER JOIN professor p ON ps.prof_id = p.professor_id " +
" INNER JOIN student_subject_marks sm ON sm.student_id = s.user_id and sm.subject_id = subj.id" +
" INNER JOIN grade g ON sm.grade_id = g.grade_id " +
"WHERE fid = ?";
PreparedStatement ps = connection.prepareStatement(select);
ps.setInt(1, id);
//
ResultSet rs = ps.executeQuery();
String professorID = rs.getString("professor_id");
Professor professor = null;
while(rs.next())
{
if (!professorMap.containsKey(professorID)) {
professor = new Professor();
professor.setProfessor_id(rs.getInt("professor_id"));
professor.setFirst_name(rs.getString("first_name"));
professor.setLast_name(rs.getString("last_name"));
professor.setTitle(rs.getString("title"));
professorMap.put(professorID, professor);
}
else{
professor = (Professor) professorMap.get(professorID);
}
}
}
catch(Exception e)
{
System.out.println("GetProfessor: " + e);
}
return professorMap;
}
This method Gets the grades:
private HashMap<String,List<StudentMark>> getStudentSubjectMarks(int id){
Connection connection = null;
HashMap<String,List<StudentMark>> studentMark=new HashMap<>();
try{
connection = new MysqlDbConnectionService().getConnection();
String select = "SELECT f.fid, f.fname, f.university_id, s.user_id, s.username, s.password, s.fullname, s.email, "+
" s.email, subj.id , subj.name , p.professor_id, p.first_name, p.last_name, p.title, g.grade_id, g.mark, g.description" +
" FROM faculty f " +
" INNER JOIN student_faculty sf ON sf.faculty_id=f.fid " +
" INNER JOIN student s ON sf.student_id=s.user_id " +
" INNER JOIN faculty_subject fs ON f.fid = fs.faculty_id " +
" INNER JOIN subject subj ON fs.subject_id = subj.id " +
" INNER JOIN professor_subject ps ON ps.subject_id = subj.id " +
" INNER JOIN professor p ON ps.prof_id = p.professor_id " +
" INNER JOIN student_subject_marks sm ON sm.student_id = s.user_id and sm.subject_id = subj.id" +
" INNER JOIN grade g ON sm.grade_id = g.grade_id " +
"WHERE fid = ?";
PreparedStatement ps = connection.prepareStatement(select);
ps.setInt(1, id);
//
ResultSet rs = ps.executeQuery();
String markID = rs.getString("grade_id");
StudentMark mark = null;
while(rs.next())
{
if (!studentMark.containsKey(markID)) {
mark = new StudentMark();
mark.setGrade_id(rs.getInt("grade_id"));
mark.setMark(rs.getInt("mark"));
mark.setDescription(rs.getString("description"));
studentMark.put(markID, (List<StudentMark>) mark);
}
else{
mark = (StudentMark) studentMark.get(markID);
}
}
}
catch(Exception e)
{
System.out.println("getStudentSubjectMark: " + e);
}
return studentMark;
}
Here is the Subject and Student Class:
Student Class:
package com.common.db.domain;
import com.google.gson.annotations.SerializedName;
import java.util.List;
public class Student {
#SerializedName("id")
private String id;
#SerializedName("username")
private String username;
#SerializedName("password")
private String password;
#SerializedName("fullname")
private String fullName;
#SerializedName("email")
private String email;
#SerializedName("subjects")
private List<Subject> subjectList;
public Student() {
}
public Student(String id, String username, String password, String fullName, String email) {
super();
this.id = id;
this.username = username;
this.password = password;
this.fullName = fullName;
this.email = email;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getFullName() {
return fullName;
}
public void setFullName(String fullName) {
this.fullName = fullName;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public List<Subject> getSubjectList() {
return subjectList;
}
public void setSubjectList(List<Subject> subjectList) {
this.subjectList = subjectList;
}
}
Subject Class:
package com.common.db.domain;
import com.google.gson.annotations.SerializedName;
import java.util.List;
public class Subject {
#SerializedName("id")
private int id;
#SerializedName("name")
private String name;
#SerializedName("Professor")
private List<Professor> professorList;
#SerializedName("Grade")
private List<StudentMark> markList;
public Subject() {
this.id = id;
this.name=name;
}
public void setId(int id)
{
this.id=id;
}
public int getId()
{
return id;
}
public void setName(String name)
{
this.name=name;
}
public String getName()
{
return name;
}
public List<Professor> getProfessorList() {
return professorList;
}
public void setProfessorList(List<Professor> professorList) {
this.professorList = professorList;
}
public List<StudentMark> getMarkList() {
return markList;
}
public void setMarkList(List<StudentMark> markList) {
this.markList = markList;
}
}
I know I have not defined the methods properly and not interlinked the 3 methods with the main method properly , so what changes do I need to do in the code for those methods to return the faculty data properly.
Here is the solution of my problem:
I've made substantial changes to the methods:
This is the main method which the GET request is calling:
public List<Faculty> getFacultiesIncludingSubObjects() throws Exception {
Connection connection = null;
List<Faculty> faculties=getFaculty();
HashMap<String, List<Subject>> studentSubjectMap = new HashMap<>();
HashMap<String, List<StudentMark>> studentSubjectGradeMap = new HashMap<>();
HashMap<String, List<Student>> facultyStudentMap = new HashMap<>();
try {
connection = new MysqlDbConnectionService().getConnection();
studentSubjectMap=getStudentSubjectMap(connection);
studentSubjectGradeMap=getStudentSubjectGradeMap(connection);
facultyStudentMap=getFacultyStudentMap(connection);
}finally {
connection.close();
}
for(Faculty faculty:faculties){
faculty.setStudentList(facultyStudentMap.get(faculty.getFid()+""));
if(faculty.getStudentList()!=null){
for(Student student:faculty.getStudentList()){
student.setSubjectList(studentSubjectMap.get(student.getId()));
if(student.getSubjectList()!=null){
for(Subject sb:student.getSubjectList()){
sb.setMarkList(studentSubjectGradeMap.get(student.getId()+"_"+sb.getId()));
}
}
}
}
}
return faculties;
}
This line: List<Faculty> faculties=getFaculty();
Calls the getFaculty method:
public ArrayList<Faculty> getFaculty() throws Exception {
ArrayList<Faculty> data = new ArrayList<Faculty>();
Connection connection = null;
try {
connection = new MysqlDbConnectionService().getConnection();
String select = "select * from faculty";
PreparedStatement ps = connection.prepareStatement(select);
ResultSet rs = ps.executeQuery();
Faculty model = null;
while (rs.next()) {
model = new Faculty();
model.setFid(rs.getInt("fid"));
model.setUniversityid(rs.getInt("university_id"));
model.setFname(rs.getString("fname"));
data.add(model);
}
} catch (Exception e) {
System.out.println(e + "Retrieve not successful");
}
return data;
}
Also inside the main method 3 more methods are called:
Subject Method:
public HashMap<String, List<Subject>> getStudentSubjectMap(Connection connection) throws SQLException {
HashMap<String, List<Subject>> result=new HashMap<>();
PreparedStatement ps = connection.prepareStatement("select s.user_id as student_id,sb.*\n" +
"from student s\n" +
" inner join student_faculty sf on s.user_id = sf.student_id\n" +
" inner join faculty f on sf.faculty_id = f.fid\n" +
" inner join faculty_subject fs on f.fid = fs.faculty_id\n" +
" inner join subject sb on fs.subject_id = sb.id;");
ResultSet rs=ps.executeQuery();
while(rs.next()){
String studentId=rs.getString("student_id");
result.putIfAbsent(studentId,new ArrayList<>());
Subject subject=new Subject();
subject.setId(rs.getInt("sb.id"));
subject.setName(rs.getString("sb.name"));
result.get(studentId).add(subject);
}
return result;
}
Student Method:
public HashMap<String, List<Student>> getFacultyStudentMap(Connection connection) throws SQLException {
HashMap<String, List<Student>> result=new HashMap<>();
PreparedStatement ps = connection.prepareStatement("select sf.faculty_id, s.*\n" +
"from student s\n" +
" inner join student_faculty sf on sf.student_id = s.user_id;");
ResultSet rs=ps.executeQuery();
while(rs.next()){
String facultyId=rs.getString("faculty_id");
result.putIfAbsent(facultyId,new ArrayList<>());
Student student=new Student();
student.setId(rs.getString("user_id"));
student.setUsername(rs.getString("username"));
student.setPassword(rs.getString("password"));
student.setFullName(rs.getString("fullname"));
student.setEmail(rs.getString("email"));
result.get(facultyId).add(student);
}
return result;
}
Grade Method:
public HashMap<String, List<StudentMark>> getStudentSubjectGradeMap(Connection connection) throws SQLException {
HashMap<String, List<StudentMark>> result=new HashMap<>();
PreparedStatement ps = connection.prepareStatement("select concat_ws('_', s.user_id, sb.id) as student_subject, sb.name, g.*\n" +
"from student s\n" +
" inner join student_faculty sf on s.user_id = sf.student_id\n" +
" inner join faculty f on sf.faculty_id = f.fid\n" +
" inner join faculty_subject fs on f.fid = fs.faculty_id\n" +
" inner join subject sb on fs.subject_id = sb.id\n" +
" inner join student_subject_marks ssm on sb.id = ssm.subject_id and ssm.student_id = s.user_id\n" +
" inner join grade g on ssm.grade_id = g.grade_id;");
ResultSet rs=ps.executeQuery();
while(rs.next()){
String studentSubjectId=rs.getString("student_subject");
result.putIfAbsent(studentSubjectId,new ArrayList<>());
StudentMark mark=new StudentMark();
mark.setMark(rs.getInt("mark"));
mark.setDescription(rs.getString("description"));
result.get(studentSubjectId).add(mark);
}
return result;
}
And the Jersey method that calls the main method is:
#GET
public Response getFaculty() throws Exception {
return Response.ok(new Gson().toJson(facultyService.getFacultiesIncludingSubObjects())).build();
}
I have data that looks like this in console:
"to add:
rand_num = 1-231881-6-70885-12
name = heat boy
type = caucasian
price = 700.0
date = 2018-08-01"
Instead I get this for some reason in database:
"to add:
rand_num = 1-231881-6-70885-12
name = heat boy
type = caucasian
price = 70"
My controller:
public class Controller {
private description = "to add: \n"+
"rand_num = 1-231881-6-70885-12 \n"+
"name = heat boy \n"+
"type = caucasian \n"+
"price = 700.0 \n"+
"date = 2018-08-01"
private Model textFields() {
Model model = new Model();
model.setRand_num(description.getText());
}
try {
DAOClass daoClass = new DAOCLass();
daoClass.insert(textFields());
}
catch(SQLException e){
System.out.println(e);
}catch(ClassNotFoundException e) {
System.out.println(e);
}
}
My model:
public class model {
private SimpleStringProperty description;
public Model() {
this("");
}
public model(String description) {
super();
this.rand_num = new SimpleStringProperty(description);
}
//getter
public String getDescription() {
return description.get();
}
//setter
public void setDescription(String description) {
this.description.set(description);
}
//property
public StringProperty descriptionProperty(){
return description;
}
#Override
public String toString() {
return "to add: " +
}
}
DAO class
public class DAO {
public void insert(Model model) throws SQLException, ClassNotFoundException {
//initializing PreparedStatement
PreparedStatement preparedStatement = null;
String updateQuery =
"INSERT INTO modelDB \n" +
"(description) \n" +
"VALUES \n" +
"(?)";
//Execute DELETE operation
try {
preparedStatement = connection.prepareStatement(updateQuery);
preparedStatement.setString(1, model.description());
preparedStatement.executeUpdate();
} catch (SQLException e) {
System.out.print("Error: " + e);
throw e;
}
finally {
if(preparedStatement != null)
{
preparedStatement.close();
}
}
}
}
My SQLite table structure:
CREATE TABLE userActivityLogs (
logId INTEGER PRIMARY KEY AUTOINCREMENT,
description VARCHAR (10000)
);
Now I know there is no limit for SQLite and even if there was I am using varChar(10000). It all displays perfectly on console but once it is in the database it is truncated. Why is that and how can I fix this issue?
I dont´t see your random number truncated so the varchar(10000) isn´t at play here.
What i see in your code is:
preparedStatement.setString(4, model.getPrice());
preparedStatement.setString(4, model.getDate());
You are using the same index for Price and Date.
I'm trying to write a small java application that returns the details for an employee. Here's my Employee class.
public class Employees {
private int id;
private Date dateofBirth;
private String firstName;
private String lastName;
private enum gender{
M, F;
}
private gender employeeGender;
private Date dateHired;
public String getEmployeeGender() {
return this.employeeGender.name();
}
public void setEmployeeGender(String employeeGender) {
this.employeeGender = gender.valueOf(employeeGender);
}
/*Getters, setters omitted*/
Here's my DAO class
public class EmployeeDao {
final String TABLE_EMPLOYEES = "employees";
final String COLUMN_EMPLOYEES_ID = "emp_no";
final String COLUMN_EMPLOYEES_DOB = "birth_date";
final String COLUMN_EMPLOYEES_FIRST_NAME = "first_name";
final String COLUMN_EMPLOYEES_LAST_NAME = "last_name";
final String COLUMN_EMPLOYEES_GENDER = "gender";
final String COLUMN_EMPLOYEES_HIRE_DATE = "hire_date";
final String QUERY_EMPLOYEES = "SELECT * FROM " + TABLE_EMPLOYEES + " WHERE " + COLUMN_EMPLOYEES_ID + " = ?";
public Employees getEmployeeDetails(int employeeId) {
Employees employee = new Employees();
try (DbConnection dbConnection = new DbConnection();
Connection databaseConnection = dbConnection.getConn();
PreparedStatement selectFromEmployees = databaseConnection.prepareStatement(QUERY_EMPLOYEES)) {
selectFromEmployees.setInt(1, employeeId);
try (ResultSet result = selectFromEmployees.executeQuery()) {
if (result.next() == false) {
System.out.println("Empty Resultset");
}
while (result.next()) {
employee.setId(result.getInt(COLUMN_EMPLOYEES_ID));
employee.setFirstName(result.getString(COLUMN_EMPLOYEES_FIRST_NAME));
employee.setLastName(result.getString(COLUMN_EMPLOYEES_LAST_NAME));
employee.setDateofBirth(result.getDate(COLUMN_EMPLOYEES_DOB));
employee.setEmployeeGender(result.getString(COLUMN_EMPLOYEES_GENDER));
employee.setDateHired(result.getDate(COLUMN_EMPLOYEES_HIRE_DATE));
}
}
} catch (Exception e) {
e.printStackTrace();
}
return employee;
}
}
But when I try to run the app in main method like this, I get an output with null values.
public static void main(String[] args) {
EmployeeDao employeeDao = new EmployeeDao();
Employees employees = employeeDao.getEmployeeDetails(39256);
System.out.println(employees.getId() + " \n" + employees.getFirstName() + " \n" + employees.getLastName() + " \n" + employees.getDateofBirth() + " \n" + employees.getDateHired());
}
This is the output.
This is how the corresponding row looks like in the database
You should not call next twice, since it will move the cursor forward again. Try this:
if (result.next() == false) {
System.out.println("Empty Resultset");
} else {
employee.setId(result.getInt(COLUMN_EMPLOYEES_ID));
employee.setFirstName(result.getString(COLUMN_EMPLOYEES_FIRST_NAME));
employee.setLastName(result.getString(COLUMN_EMPLOYEES_LAST_NAME));
employee.setDateofBirth(result.getDate(COLUMN_EMPLOYEES_DOB));
employee.setEmployeeGender(result.getString(COLUMN_EMPLOYEES_GENDER));
employee.setDateHired(result.getDate(COLUMN_EMPLOYEES_HIRE_DATE));
}
Calling ResultSet#next moves the cursor forward a row, so your if condition loses the first row. Since you know your query can return at most one row, you don't need the while loop at all, however:
public Employees getEmployeeDetails(int employeeId) throws SQLException {
Employees employee = null;
try (DbConnection dbConnection = new DbConnection();
Connection databaseConnection = dbConnection.getConn();
PreparedStatement selectFromEmployees =
databaseConnection.prepareStatement(QUERY_EMPLOYEES)) {
selectFromEmployees.setInt(1, employeeId);
try (ResultSet result = selectFromEmployees.executeQuery()) {
if (result.next()) {
employee = new Employees();
employee.setId(result.getInt(COLUMN_EMPLOYEES_ID));
employee.setFirstName(result.getString(COLUMN_EMPLOYEES_FIRST_NAME));
employee.setLastName(result.getString(COLUMN_EMPLOYEES_LAST_NAME));
employee.setDateofBirth(result.getDate(COLUMN_EMPLOYEES_DOB));
employee.setEmployeeGender(result.getString(COLUMN_EMPLOYEES_GENDER));
employee.setDateHired(result.getDate(COLUMN_EMPLOYEES_HIRE_DATE));
}
}
}
return employee;
}
No need to add extra result.next() comparison.
if (result.next() == false) {
System.out.println("Empty Resultset");
}
while (result.next()){
}
while will execute only if there are any rows.
Check the size of list generated before using to check if it contains value or not.
Just to let you know:
I know how to use Scanner od BufferedReader, just dont know where to use it in this case.
I am working on my first bigger app in Java.
(I had to use SQLite as a DB)
That's some kind of gym app, where I will add my workouts (4 simple variables)
And then it will be saved in DB and sorted to read out.
My question is...
How should I add an Input from the user?
I have setters and getters and no Idea where this input should be added.
In main class? Should I build a new method?
package bazadanych;
import java.util.List;
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
DBConnector d = new DBConnector();
d.addWorkout( "bicek", 12, 5,22052019);
List<Workout> workouts = d.allWorkouts();
for (int i=0; i < workouts.size(); i++) {
System.out.println("---------------------------------");
System.out.println("The name of the excersise: " + workouts.get(i).getName());
System.out.println(" Number of reps: " + workouts.get(i).getReps());
System.out.println(" Weight: " + workouts.get(i).getWeight() + "kg");
System.out.println("Date: " + workouts.get(i).getDate());
System.out.println("---------------------------------");
}
}
package bazadanych;
public class Workout extends DBConnector {
private int workoutId;
private String name;
private int reps;
private int weight;
private int date;
public Workout(int workoutId, String name, int weight, int reps, int date)
{
setWorkoutId(workoutId);
setName(name);
setWeight(weight);
setReps(reps);
setDate(date);
}
// Getters
public int getDate()
{
return date;
}
public int getWorkoutId()
{
return workoutId;
}
public String getName()
{
return name;
}
public int getReps()
{
return reps;
}
public int getWeight()
{
return weight;
}
//Setters
public void setDate(int date)
{
this.date = date;
}
public void setName(String name)
{
this.name = name;
}
public void setReps(int reps)
{
this.reps = reps;
}
public void setWorkoutId(int workoutId)
{
this.workoutId = workoutId;
}
public void setWeight(int weight)
{
this.weight = weight;
}
}
package bazadanych;
import java.sql.*;
import java.util.LinkedList;
import java.util.List;
public class DBConnector {
// connection with datebase
private Connection conn;
// The object used to execute a static SQL statement and returning the results
private Statement stat;
// Construct
public DBConnector()
{
try
{
Class.forName("org.sqlite.JDBC");
}
catch (ClassNotFoundException e)
{
System.err.println("There is no JDBC driver");
e.printStackTrace();
}
try
{
conn = DriverManager.getConnection("jdbc:sqlite:GymApp.db"); // GymApp will be the name of the datebase
stat = conn.createStatement();
}
catch (SQLException e)
{
System.err.println("I can not connect");
}
CreateStructure();
}
public boolean CreateStructure()
{
// Rule to delete the table and create new, when we want to rework number of columnes etc.
// String dropFirst = "DROP TABLE IF EXISTS workouts;";
String sql = "CREATE TABLE IF NOT EXISTS workouts"
+ "("
+ "workoutId INTEGER PRIMARY KEY AUTOINCREMENT,"
+ "name varchar(100),"
+ "reps INTEGER, "
+ " weight INTEGER,"
+ " date INTEGER"
+ ")";
try
{
// stat.execute(dropFirst);
stat.execute(sql);
}
catch (SQLException e)
{
System.err.println("There is a problem by Structure creation");
e.printStackTrace();
return false;
}
return true;
}
public boolean addWorkout( String name, int reps, int weight, int date)
{ String sql = " insert into workouts values (Null,?,?,?,?);";
try
(PreparedStatement pStmt = conn.prepareStatement(sql)){
pStmt.setString(1, name);
pStmt.setInt(2,reps);
pStmt.setInt(3,weight);
pStmt.setInt(4, date);
pStmt.execute();
}
catch(SQLException e)
{
System.err.println("Can not add a new contact");
e.printStackTrace();
return false;
}
return true;
}
public List<Workout> allWorkouts()
{
List<Workout> workouts = new LinkedList<Workout>();
try {
ResultSet show = stat.executeQuery("SELECT * FROM workouts ORDER BY date");
int id;
String name;
int reps;
int weight;
int date;
while (show.next())
{
id = show.getInt("workoutId");
name = show.getString("name");
reps = show.getInt("reps");
weight = show.getInt("weight");
date = show.getInt("date");
workouts.add(new Workout(id, name,reps,weight,date));
}
}
catch (SQLException e)
{
e.printStackTrace();
return null;
}
return workouts;
}
public void closeConnection() {
try{
conn.close();
}
catch (SQLException e) {
System.err.println("There is connection closing error");
e.printStackTrace();
}
}
}
To answer your main question, you should add the input from the user in the main method. You'd use an instance of Scanner to read the values of workout name, reps and weight. Date you could simply pick up the current date, code sample below.
A few other recommendations:
1 - Change the workout date to long, that's a standard in the industry.
2 - The method CreateStructure does not follow Java coding standards, rename it to createStructure.
3 - You are storing the workout ID as NULL, that could cause you trouble later when trying to retrieve the data from the database.
Code sample:
public static void main(String[] args) {
DBConnector d = new DBConnector();
// Retrieve input from the user
Scanner sc = new Scanner(System.in);
String name = sc.nextLine();
int reps = sc.nextInt();
int weight = sc.nextInt();
// create the workout with the data
d.addWorkout( name, reps, weight, LocalDate.now().toEpochDay());
List<Workout> workouts = d.allWorkouts();
// print workouts
}
I have a Database table with airports, each airport has a name and an ID.
In JavaFX I have a form, with a ComboBox, the combobox needs to display all the airport names and when the form is submitted it needs to insert the ID of the airport into the database (not its name).
But I'm not really figuring out what the solution is.
I have a
ObservableList vliegveldenList = FXCollections.observableArrayList();
ObservableList vliegveldenIDList = FXCollections.observableArrayList();
Database connection to fill the ComboBox
ResultSet rs = Project_Fasten_Your_Seatbelt.conn.createStatement()
.executeQuery("SELECT vliegveldnaam, vliegveld_id FROM fys_project.vliegvelden;");
while (rs.next()) {
vliegveldenList.add(rs.getString(1));
vliegveldenIDList.add(rs.getString(2));
}
Fills the combobox:
vliegveldHerkomst.setValue("Luchthaven ...");
vliegveldHerkomst.setItems(vliegveldenList);
And this is added to the database when button is pressed:
String registratieValue = registratieNmrTxt.getText();
String vluchtValue = vluchtNrmTxt.getText();
String vliegveldValue = (String) vliegveldHerkomst.getSelectionModel().getSelectedItem();
String bestemmingValue = (String) vliegveldBestemming.getSelectionModel().getSelectedItem();
String gevondenValue = (String) vliegveldGevonden.getSelectionModel().getSelectedItem();
LocalDate dGevondenValue = datumGevondenDate.getValue();
LocalDate dVluchtValue = datumVluchtDate.getValue();
String gewichtValue = gewichtBagageTxt.getText();
String kleurenValue = (String) kleuren.getSelectionModel().getSelectedItem();
String kofferValue = (String) kofferMerken.getSelectionModel().getSelectedItem();
String opmerkingValue = opmerkingArea.getText();
//Data gevonden bagage invoeren
Project_Fasten_Your_Seatbelt.conn.createStatement().executeUpdate(
"INSERT INTO gevondenbagage "
+ "(registratienummer, datumgevonden, datumaangemeld, vliegveldherkomst, "
+ "vliegveldbestemming, vliegveldgevonden, vluchtnummer, vluchtdatum, gewicht, "
+ "kleur, merk, `speciale opmerkingen`, userid)"
+ "VALUES ('" + registratieValue + "','" + dGevondenValue + "','" + today.format(localDate) + "','"
+ vliegveldValue + "','" + bestemmingValue + "','" + gevondenValue + "','"
+ vluchtValue + "','" + dVluchtValue + "','" + gewichtValue + "','"
+ kleurenValue + "','" + kofferValue + "','" + opmerkingValue + "','"
+ Project_Fasten_Your_Seatbelt.getUserId() + "')");
This all works okay, but instead of the name of the airport I want to set the ID for the airport for vliegveldValue.
How do I do this?
You can create e.g. an AirPort class with ID and name members and a ComboBox that displays these objects: ComboBox<AirPort>.
AirPort class:
public class AirPort {
private int ID;
private String name;
public AirPort(int id, String name) {
this.ID = id;
this.name = name;
}
public int getID() { return ID; }
public String getName() { return name; }
}
Get the items from the DB and create the ComboBox:
// Fill the list from the DataBase
ObservableList<AirPort> airports = FXCollections.observableArrayList();
airports.addAll(new AirPort(0, "Heathrow"),
new AirPort(1, "Frankfurt"),
new AirPort(2, "NewYork"));
ComboBox<AirPort> combo = new ComboBox<>();
combo.setItems(airports);
Finally to display the name of the objects you can use for example a StringConverter:
combo.setConverter(new StringConverter<AirPort>() {
#Override
public String toString(AirPort object) {
return object.getName();
}
#Override
public AirPort fromString(String string) {
return combo.getItems().stream().filter(ap ->
ap.getName().equals(string)).findFirst().orElse(null);
}
});
And then when the value is changing you get back AirPort objects which contains the needed ID:
combo.valueProperty().addListener((obs, oldval, newval) -> {
if(newval != null)
System.out.println("Selected airport: " + newval.getName()
+ ". ID: " + newval.getID());
});
Your Airport Class.. .
public class Airport {
private int id;
private String name;
public Airport(int id, String name) {
super();
this.id = id;
this.name = name;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}// class Airport
Create Observable list of Airport
ObservableList<AirPort> airports = FXCollections.observableArrayList();
airports.add(new Airport(1, "Beijing Capital International Airport"));
airports.add(new Airport(2, "Los Angeles International Airport"));
airports.add(new Airport(3, "London Heathrow Airport"));
Set item of your combo box. .
combo.setItems(airports);
After this when you run your program you get the output like this. ..
To get name of Airports you have to need to override toString method in Airport class.
#Override
public String toString() {
return this.getName();
}
After this you will get output like.. .
Now to get the id of selected airport you can set an event handler. .
private void setEventOnAirport() {
combo.setOnKeyReleased(event -> {
if (event.getCode().equals(KeyCode.ENTER)) {
Airport airport = combo.getSelectionModel().getSelectedItem();
System.out.println(airport.getId());
}
});
}
By this function you can see the ID of selected Airport. . .