Skip to content

Commit

Permalink
☀️ Landing jobs integration! (#11)
Browse files Browse the repository at this point in the history
* landing jobs integration

* remove unwanted file

* trim spaces on titles

* fix readme menu
  • Loading branch information
Sérgio Martins committed Oct 24, 2020
1 parent dfed19f commit 59e7b30
Show file tree
Hide file tree
Showing 8 changed files with 516 additions and 373 deletions.
788 changes: 418 additions & 370 deletions README.md

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion docs/CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ The process described here has several goals:
Please follow these steps to have your contribution considered:

1. Follow all instructions in [the template](../.github/pull_request_template.md)
1. Follow the [styleguides](#styleguides)
1. Follow the [styleguide](#styleguide)
3. After you submit your pull request, verify that all [status checks](https://help.github.com/articles/about-status-checks/) are passing

<details>
Expand Down
1 change: 1 addition & 0 deletions docs/README_TEMPLATE.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ _An awesome curated list of the most recent QA vacancies in Portugal, updated ev
* [Glassdor](#glassdoor)
* [Indeed](#indeed)
* [ItJobs](#itjobs)
* [LandingJobs](#landingjobs)

## About
Inspired by the COVID-19 tragic events of unemployment arising within my network connections, I decided to develop this open-source project with the goal of supporting those who are tireless looking for a new QA opportunity here, in my beloved Portugal.
Expand Down
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

<groupId>qa.vacancies.portugal</groupId>
<artifactId>qa-vacancies-in-portugal</artifactId>
<version>1.3.0</version>
<version>1.4.0</version>
<packaging>jar</packaging>

<name>qa-vacancies-in-portugal</name>
Expand Down
3 changes: 3 additions & 0 deletions src/main/java/qa/vacancies/portugal/Application.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
import qa.vacancies.portugal.vacancies.GlassdoorVacancies;
import qa.vacancies.portugal.vacancies.IndeedVacancies;
import qa.vacancies.portugal.vacancies.ItJobsVacancies;
import qa.vacancies.portugal.vacancies.LandingJobsVacancies;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
Expand All @@ -20,6 +21,7 @@ public class Application {
private static final MarkdownStringBuilder GLASSDOOR_VACANCIES = new GlassdoorVacancies();
private static final MarkdownStringBuilder INDEED_VACANCIES = new IndeedVacancies();
private static final MarkdownStringBuilder IT_JOBS_VACANCIES = new ItJobsVacancies();
private static final MarkdownStringBuilder LANDING_JOBS_VACANCIES = new LandingJobsVacancies();

/**
* Magic.
Expand All @@ -31,6 +33,7 @@ public static void main(String[] args) {
MarkdownFileWriter.appendMarkdown(README, GLASSDOOR_VACANCIES.stringBuilder());
MarkdownFileWriter.appendMarkdown(README, INDEED_VACANCIES.stringBuilder());
MarkdownFileWriter.appendMarkdown(README, IT_JOBS_VACANCIES.stringBuilder());
MarkdownFileWriter.appendMarkdown(README, LANDING_JOBS_VACANCIES.stringBuilder());
}

private static StringBuilder lastUpdated() {
Expand Down
2 changes: 1 addition & 1 deletion src/main/java/qa/vacancies/portugal/pages/ItJobsPage.java
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ private boolean containsQuery(SelenideElement element) {
}

private String getTitle(SelenideElement element) {
return element.$(TITLE_SELECTOR).getText();
return element.$(TITLE_SELECTOR).getText().trim();
}

private String getCompany(SelenideElement element) {
Expand Down
59 changes: 59 additions & 0 deletions src/main/java/qa/vacancies/portugal/pages/LandingJobsPage.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
package qa.vacancies.portugal.pages;

import com.codeborne.selenide.SelenideElement;
import qa.vacancies.portugal.utils.constants.Constants;
import qa.vacancies.portugal.utils.model.Vacancy;

import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import static com.codeborne.selenide.Condition.visible;
import static com.codeborne.selenide.Selenide.$;
import static com.codeborne.selenide.Selenide.$$;
import static com.codeborne.selenide.Selenide.open;

public class LandingJobsPage implements PageObject<LandingJobsPage> {
private static final String SEARCH_SPINNER_SELECTOR = "#search_spinner";
private static final String CARD_SELECTOR = ".lj-jobcard ";
private static final String TITLE_SELECTOR = ".lj-jobcard-name";
private static final String LIST_NAME_SELECTOR = ".lj-jobcard-company";

@Override
public LandingJobsPage openAndSearch(String urlTemplate, Object... params) {
Object[] nonNullParams = Arrays.stream(params).filter(Objects::nonNull).toArray();
open(String.format(urlTemplate, nonNullParams));
return this;
}

@Override
public List<Vacancy> getVacancies() {
$(SEARCH_SPINNER_SELECTOR).shouldNotBe(visible);

return $$(CARD_SELECTOR)
.stream()
.filter(this::containsQuery)
.map(element -> Vacancy.builder().title(getTitle(element)).company(getCompany(element)).url(getUrl(element)).build())
.collect(Collectors.toList());
}

private boolean containsQuery(SelenideElement element) {
return Stream
.of(Constants.KEYWORDS)
.anyMatch(keyword -> element.$(TITLE_SELECTOR).innerText().toLowerCase().contains(keyword));
}

private String getTitle(SelenideElement element) {
return element.$(TITLE_SELECTOR).innerText().trim();
}

private String getCompany(SelenideElement element) {
return element.$(LIST_NAME_SELECTOR).innerText();
}

private String getUrl(SelenideElement element) {
return element.$(TITLE_SELECTOR).getAttribute("href");
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
package qa.vacancies.portugal.vacancies;

import qa.vacancies.portugal.pages.LandingJobsPage;
import qa.vacancies.portugal.pages.PageObject;
import qa.vacancies.portugal.utils.model.Location;

public class LandingJobsVacancies extends Vacancies {
private static final String URL_TEMPLATE = "https://landing.jobs/jobs?page=1&location=%s&lr=0&match=all&country=PT&q=%s";
private static final String URL_TEMPLATE_REMOTE = "https://landing.jobs/jobs?page=1&lr=0&fr=true&match=all&q=%s";

private static final Location AVEIRO = Location.builder().urlTemplate(URL_TEMPLATE).id("Aveiro, Portugal&city=Aveiro").build();
private static final Location BRAGA = Location.builder().urlTemplate(URL_TEMPLATE).id("Braga, Portugal&city=Braga").build();
private static final Location COIMBRA = Location.builder().urlTemplate(URL_TEMPLATE).id("Coimbra, Portugal&city=Coimbra").build();
private static final Location LISBOA = Location.builder().urlTemplate(URL_TEMPLATE).id("Lisbon, Portugal&city=Lisbon").build();
private static final Location PORTO = Location.builder().urlTemplate(URL_TEMPLATE).id("Porto, Portugal&city=Porto").build();
private static final Location REMOTE = Location.builder().urlTemplate(URL_TEMPLATE_REMOTE).build();

private final PageObject<LandingJobsPage> landingJobsPage;

public LandingJobsVacancies() {
super(AVEIRO, BRAGA, COIMBRA, LISBOA, PORTO, REMOTE);
landingJobsPage = new LandingJobsPage();
}

@Override
public StringBuilder stringBuilder() {
StringBuilder sb = new StringBuilder();
appendWebsite(sb, "LandingJobs");
appendVacancies(sb, landingJobsPage);
return sb;
}
}

0 comments on commit 59e7b30

Please sign in to comment.