Trabalhei no projeto da API com o Parceiro Acadêmico Embraer.
A Embraer é uma empresa renomada e importantíssima para o Brasil, produzindo aeronaves que são exportadas para dezenas de países e também utilizadas em solo brasileiro. Com o grande número de aeronaves produzidas, a construção e manutenção da documentação da aeronave - que pode chegar a milhares de páginas - torna-se algo complexo, portanto procuravam uma solução digital e moderna para a varredura e montagem de PDFs e leitura automatizada de Excel.
Java SE 8, MySQL, IDE Eclipse, GitHub, IText, Maven e Framework Springboot
Fui responsável pela maioria do backend, pela arquitetura MVC, regras de serviço e "raspagem" de dados.
- O maior desafio do projeto. A lógica de programação para executar a raspagem de dados dos manuais em formato pdf, como ainda estávamos sendo introduzidos a programação mais avançada (que lida com estruturas de dados) precisei estudar em todo tempo livre que tive para aprender novas estruturas e saber onde aplica-las também usei muito a biblioteca externa itextpdf.
Controller da LEP, parte do sistema que recebia dados via excel
Controller
@Controller
public class LEPController {
private final LepService lepService;
public LEPController(LepService lepService) {
this.lepService = lepService;
}
@RequestMapping("/lep-create")
public String showLepCreatePage(Model model) {
Lep lep = new Lep();
model.addAttribute("lep", lep);
return "lep-create";
}
@PostMapping(value = "/lep-create")
public String createLep(@ModelAttribute("lep") Lep lep,
RedirectAttributes redirAttrs) throws IOException {
if(!lepService.checkIntegrity(lep)) {
redirAttrs.addFlashAttribute("error", "Incorrect data, check" +
" fields integrity, eg.: all fields are filled?");
return "redirect:/lep-create";
}
lepService.createLep1(lep);
redirAttrs.addFlashAttribute("success", "LEP successfully created!");
return "redirect:/lep-create";
}
}
Esse repository faz a conexão entre o backend e banco de dados, procurando manual pelo nome e checando quantos manuais existem com o nome informado
Repository
@Repository
public interface ManualRepository extends JpaRepository<Manual, Integer> {
@Query(" select mnl_id from Manual where mnl_name = ?1 ")
Integer findManualByName(String nomeManual);
@Query("select count(mnl_id) from Manual where mnl_name = ?1")
Long checkCount(String nomeManual);
}
O service da principal funcionalidade do projeto, raspagem de dados dos arquivos pdfs dos manuais.
Service (raspagem de dados!)
@Service
public class LepService
{
private final ManualService manualService;
private final CodeListService codeListService;
private String currentRevision;
@Autowired
public LepService(ManualService manualService, CodeListService codeListService) {
this.manualService = manualService;
this.codeListService = codeListService;
this.currentRevision = "";
}
public boolean checkIntegrity(Lep lep) {
if(lep.getRevision_dates().length() == 0) {
return false;
} else if(lep.getCdl_code().length() == 0){
return false;
} else if(lep.getMnl_name().length() == 0) {
return false;
} else return lep.getFlg_tag().length() != 0;
}
public void createLep1(final Lep lep) throws IOException {
List<String> filterRevisionDates = new ArrayList<>();
final String[] rvParts = lep.getRevision_dates().split("-");
for (int i = 0; i < rvParts.length; ++i) {
StringBuilder rvFinal = new StringBuilder();
for (int j = 0; j < rvParts[i].length(); ++j) {
rvFinal.append(rvParts[i].charAt(j));
if (j == 7 || j == 8) {
rvFinal.append(".................");
}
if(i == rvParts.length-1 && j <= 8) {
if(Character.isDigit(rvParts[i].charAt(j))) {
if(Character.isDigit(rvParts[i].charAt(j+1))) {
currentRevision+= " ";
} else {
currentRevision+=" 0";
}
}
currentRevision+=rvParts[i].charAt(j);
}
}
filterRevisionDates.add(rvFinal.toString());
}
final Integer mnl_id = this.manualService.findManualByName(lep.getMnl_name());
this.createLep2(lep, mnl_id, filterRevisionDates);
}
public void addCell(String block, String code, Integer page,
String change, Table table, Integer lastPage) {
if (page == 1) {
table.addCell(new Cell().add(block).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderTop(new SolidBorder(0.5f)));
table.addCell(new Cell().add(code).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderTop(new SolidBorder(0.5f)));
table.addCell(new Cell().add(String.valueOf(page)).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderTop(new SolidBorder(0.5f)));
if (change.equals(currentRevision)) {
table.addCell(new Cell().add("*").setBorder(Border.NO_BORDER)
.setBorderTop(new SolidBorder(0.5f)));
} else {
table.addCell(new Cell().add("").setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderTop(new SolidBorder(0.5f)));
}
table.addCell(new Cell().add(change).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderTop(new SolidBorder(0.5f)));
} else if (page == lastPage) {
table.addCell(new Cell().add(block).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderBottom(new SolidBorder(0.5f)));
table.addCell(new Cell().add(code).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderBottom(new SolidBorder(0.5f)));
table.addCell(new Cell().add(String.valueOf(page)).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderBottom(new SolidBorder(0.5f)));
if (change.equals(currentRevision)) {
table.addCell(new Cell().add("*").setBorder(Border.NO_BORDER)
.setBorderBottom(new SolidBorder(0.5f)));
} else {
table.addCell(new Cell().add("").setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderBottom(new SolidBorder(0.5f)));
}
table.addCell(new Cell().add(change).setBorder(Border.NO_BORDER).setTextAlignment(TextAlignment.CENTER)
.setBorderBottom(new SolidBorder(0.5f)));
} else {
table.addCell(new Cell().add(block).setBorder(Border.NO_BORDER)).setTextAlignment(TextAlignment.CENTER);
table.addCell(new Cell().add(code).setBorder(Border.NO_BORDER)).setTextAlignment(TextAlignment.CENTER);
table.addCell(new Cell().add(String.valueOf(page)).setBorder(Border.NO_BORDER)).setTextAlignment(TextAlignment.CENTER);
if (change.equals(currentRevision)) {
table.addCell(new Cell().add("*").setBorder(Border.NO_BORDER));
}
else {
table.addCell(new Cell().add("").setBorder(Border.NO_BORDER)).setTextAlignment(TextAlignment.CENTER);
}
table.addCell(new Cell().add(change).setBorder(Border.NO_BORDER)).setTextAlignment(TextAlignment.CENTER);
}
}
...
}
- Esse foi um dos projetos que mais contribui e de maneira essencial para o sucesso do grupo.
- JPA
- Primeiro contato com essa API extremamente utilizada no mercado de trabalho Java, abstrai a comunicação entre back e banco de dados de forma intuitiva.
- Sei fazer com autonomia.
- Uso de arquitetura MVC
- Como o projeto foi mudando ao longo das sprints a arquitetura MVC ajudou muito para integração do código e adição de novas features.
- Sei fazer com autonomia.
- Uso de bibliotecas externas como IText
- O pronto focal do projeto era a "raspagem" de dados dos manuais portanto o uso dessa api externa foi essêncial para a finalização do projeto, assim percebi que como desenvolvedor não preciso criar tudo do zero, posso aprender a utilizar apis e ferramentas já sólidas na comunidade.
- Sei fazer com ajuda.
- Implementação de exceptions
- Algo extremamente importante para tornar-se um bom programador.
- Sei fazer com autonomia.
- Spring boot
- Framework completo e muito utilizado no mercado de trabalho Java, de fácil configuração e facilidade de boot já que usa servidor acoplado.
- Sei fazer com autonomia.
Esse projeto teve uma complexidade muito alta, principalmente para o momento do curso, porém, tendo a resiliência adquirida em outros projetos consegui, com autonomia, estudar e aprender o que era necessário para desenvolver o projeto. Porém nem sempre força de vontade resolve, precisei ser criativo para resolver algumas questões da implementação e contei com a ajuda dos professores em questões de hard skills e soft skills comunicando minhas dificuldades em certos aspectos do projeto. Outro ponto interessante foi na raspagem de dados, como nem sempre o usuário seguia um padrão de digitação foi minha responsabilidade achar esse padrão inusitado, foi necessária uma boa dose de paciência para encontrá-lo.