Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

implemented fruit shop program logic using solid principles #1292

Open
wants to merge 16 commits into
base: master
Choose a base branch
from

Conversation

kriznychenko
Copy link

No description provided.

Copy link

@mateacademy-ai-mentor mateacademy-ai-mentor left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.


Thank you for your hard work on this project! While your code demonstrates a solid understanding of the task requirements, there are a few critical issues that need to be addressed before we can approve the pull request:

  1. Method Naming: The method getOperation in the OperationHandler interface and its implementations is misleading. It should be renamed to something like execute or performOperation to better reflect its purpose.

  2. Resource Management: Ensure that file handling in FileReaderImpl and FileWriterImpl uses try-with-resources to guarantee proper closure of resources and prevent potential leaks.

  3. Error Handling: Improve exception handling by providing more informative messages, especially when parsing integers or handling file operations. This will make debugging easier and improve user experience.

  4. Data Encapsulation: The Storage class should not expose its internal map directly. Return a copy of the map to prevent unintended modifications from outside the class.

  5. Constructor Redundancy: The constructor in FileWriterImpl is redundant. Consider removing it unless you plan to extend its functionality.

  6. File Path Handling: Avoid using hardcoded file paths. Use relative paths to ensure the code is portable across different environments.

By addressing these issues, you'll enhance the code's robustness and maintainability. Keep up the great work, and I'm looking forward to seeing the improvements! 😊

✨ Please rate this review in the Platform's notification center. I will be grateful for your feedback! ✨

🔄 Fix the issues, commit the changes, and then re-request my review using the Re-request review button in the Reviewers tab.


public class Main {
public static void main(String[] args) {
FileReader fileReader = new FileReaderImpl("src/main/java/db/reportToRead.csv");

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The FileReaderImpl constructor is being called with a hardcoded file path. Consider using a relative path to ensure portability across different environments .

Copy link

@mateacademy-ai-mentor mateacademy-ai-mentor left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.


Your Pull Request has been approved! 🎉

While your code meets the task requirements, there are several areas for improvement that can enhance the robustness and maintainability of your code:

  • Exception Handling: Ensure that exception messages are informative and provide context, such as row numbers or file names, to aid in debugging. Consider logging errors or adding comments to explain exceptions, especially for unknown operation codes.

  • Resource Management: Use try-with-resources for both FileReader and FileWriter to ensure proper closure and prevent resource leaks.

  • Separation of Concerns: The parseCsvRow method should be moved to a class that handles data conversion, such as DataConverterImpl, to improve separation of concerns.

  • Data Encapsulation: Avoid direct instantiation of Storage to maintain encapsulation. Use methods to access its data instead.

  • Null Handling: Add checks for potential null returns from methods like operationStrategy.get to prevent NullPointerException.

  • Constructor Redundancy: Remove redundant constructors unless additional functionality is planned.

Your efforts are commendable, and addressing these issues will help you grow as a developer. Keep up the great work and continue learning from these experiences! 🚀

✨ Please rate this review in the Platform's notification center. I will be grateful for your feedback! ✨

FileWriter fileWriter = new FileWriterImpl("finalReport.csv");
fileWriter.write(resultingReport);
} catch (IOException e) {
throw new RuntimeException("Enable to create FileWriter for finalReport.csv", e);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The exception message here could be more informative. Consider changing it to something like 'Unable to write to finalReport.csv'.

ShopService shopService = new ShopServiceImpl(operationStrategy);
shopService.process(transactions);

Storage storage = new Storage();

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Direct instantiation of Storage might expose its internal state. Consider using a method to access its data to maintain encapsulation.

Comment on lines 33 to 43
public FruitTransaction parseCsvRow(String csvRow) {
String[] fields = csvRow.split(",");
FruitTransaction fruitTransaction = new FruitTransaction();
fruitTransaction.setOperation(FruitTransaction.Operation.valueOf(fields[0]));
fruitTransaction.setFruit(fields[1]);
try {
fruitTransaction.setQuantity(Integer.parseInt(fields[2]));
} catch (NumberFormatException e) {
throw new IllegalArgumentException("Invalid quantity format: " + fields[2], e);
}
return fruitTransaction;

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The parseCsvRow method is responsible for parsing CSV rows into FruitTransaction objects, which is not directly related to file reading. Consider moving this method to a class that handles data conversion, such as DataConverterImpl, to improve separation of concerns.

try {
fruitTransaction.setQuantity(Integer.parseInt(fields[2]));
} catch (NumberFormatException e) {
throw new IllegalArgumentException("Invalid quantity format: " + fields[2], e);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The error message for Invalid quantity format is informative, but consider including the row number or more context to aid in debugging when this exception is thrown.

Comment on lines 7 to 9
public FileWriterImpl(String fileName) throws IOException {
super(fileName);
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The constructor in FileWriterImpl is redundant as it does not add any new functionality beyond calling the superclass constructor. Consider removing it unless you plan to add additional functionality.


@Override
public OperationHandler get(FruitTransaction.Operation operationType) {
return operationHandlerMap.get(operationType);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The get method may return null if the operation type is not found in the map. Consider handling this case by returning a default handler, throwing an exception, or providing a meaningful error message to avoid potential NullPointerException.

Comment on lines +19 to +20
OperationHandler handler = operationStrategy.get(transaction.getOperation());
handler.performOperation(transaction);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The operationStrategy.get method may return null if no handler is found for a given operation. Consider adding a null check and handling this case to prevent potential NullPointerException.

Copy link

@liliia-ponomarenko liliia-ponomarenko left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good job! Let’s improve your solution ;)

Comment on lines 54 to 59
try {
FileWriter fileWriter = new FileWriterImpl("finalReport.csv");
fileWriter.write(resultingReport);
} catch (IOException e) {
throw new RuntimeException("Unable to create FileWriter for finalReport.csv", e);
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the same

Comment on lines 7 to 9
public FileWriterImpl(String fileName) throws IOException {
super(fileName);
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the same

import java.io.FileWriter;
import java.io.IOException;

public class FileWriterImpl extends FileWriter {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add writing logic

@kriznychenko
Copy link
Author

Everything was understandable and clear.
Thank you with best wishes!

Copy link

@liliia-ponomarenko liliia-ponomarenko left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good job! A few minor comments. But fix it before testing your solution ;)

import strategy.OperationStrategy;

public class Main {
private static final String REPORT_TO_READ_FILE = "src/main/java/resources/reportToRead.csv";

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Create a system resources directory. It has an incorrect level

Suggested change
private static final String REPORT_TO_READ_FILE = "src/main/java/resources/reportToRead.csv";
private static final String REPORT_TO_READ_FILE = "src/main/resources/reportToRead.csv";

return fruitTransaction;
}
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change

leave only one empty line

Comment on lines +10 to +12
public FileReaderImpl() {

}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
public FileReaderImpl() {
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fix comment

}
try {
List<String> lines = Files.readAllLines(file.toPath());
return lines.subList(1, lines.size());

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

move header skipping to DataConverter. This method should only read file content

Comment on lines +24 to +25
public Map<String, Integer> getAllFruits() {
return new HashMap<>(fruits);

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fix comment

Comment on lines +10 to +12
public FileReaderImpl() {

}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fix comment


public class FileWriterImpl {
public void write(String filePath, String content) {
try (FileWriter fileWriter = new FileWriter(filePath)) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

check if FileWriter implements AutoCloseable

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants