Merge branch 'release/1.0.0' into feature/SUPPORT-8412-8413_new_request_format

# Conflicts:
#	backend/src/main/java/ru/micord/ervu/kafka/ReplyingKafkaConfig.java
#	config/patches/default.cli
#	config/standalone/dev/standalone.xml
#	frontend/src/ts/modules/app/app.module.ts
#	pom.xml
#	resources/src/main/resources/business-model/LK RP FL/mydata.page
#	resources/src/main/resources/business-model/LK RP FL/screen-form-fl.page
This commit is contained in:
gulnaz 2024-09-20 10:51:43 +03:00
commit 5030679eb9
89 changed files with 3062 additions and 4931 deletions

View file

@ -1,18 +1,23 @@
FROM tomee:8.0.15-jre17-webprofile
FROM maven:3-openjdk-17-slim AS build
RUN apt update \
&& apt upgrade -y \
&& curl -fsSL https://deb.nodesource.com/setup_14.x | bash - \
&& apt install -y git nodejs \
&& rm -rf /var/lib/apt/lists/*
RUN \
rm -rf /usr/local/tomee/webapps/ROOT && \
echo "fias.enable=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.jbpm.hibernate_statistics.enabled=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.mode=production" >> /usr/local/tomee/conf/catalina.properties && \
echo "authentication.method=form" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.cache.hazelcast.hosts=127.0.0.1" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.cache.hazelcast.outbound_port_definitions=5801-5820" >> /usr/local/tomee/conf/catalina.properties && \
echo "gar.enable=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "reset_password.mail.template.path=mail/reset_password.html" >> /usr/local/tomee/conf/catalina.properties && \
echo "security.password.regex=^(?=.*[a-zA-Z])(?=.*[0-9])[a-zA-Z0-9]+$" >> /usr/local/tomee/conf/catalina.properties && \
echo "bpmn.enable=false" >> /usr/local/tomee/conf/catalina.properties
COPY config/context.xml /usr/local/tomee/conf/
#COPY config/tomcat-users.xml /usr/local/tomee/conf/
COPY frontend/dist/ /usr/local/tomee/webapps/ROOT
COPY backend/target/*.war /usr/local/tomee/webapps/fl.war
WORKDIR /app
COPY . .
RUN mvn clean && mvn package -T4C
FROM gitlab.micord.ru:5050/common/base/webbpm/webbpm-tomcat-cprocsp:8.0.15-jre17-webprofile
ARG ADMIN_PASSWORD=Secr3t
COPY config/tomcat/tomee /usr/local/tomee
RUN rm -rf /usr/local/tomee/webapps/ROOT \
&& cat /usr/local/tomee/conf/webbpm.properties >> /usr/local/tomee/conf/catalina.properties \
&& sed -i -r "s/<must-be-changed>/$ADMIN_PASSWORD/g" /usr/local/tomee/conf/tomcat-users.xml
COPY --from=build /app/backend/libs/ /usr/local/tomee/lib/
COPY --from=build /app/frontend/target/*.war /usr/local/tomee/webapps/ROOT.war
COPY --from=build /app/backend/target/*.war /usr/local/tomee/webapps/fl.war

30
Dockerfile.old Normal file
View file

@ -0,0 +1,30 @@
FROM maven:3-openjdk-17-slim AS build
RUN apt update \
&& apt upgrade -y \
&& curl -fsSL https://deb.nodesource.com/setup_14.x | bash - \
&& apt install -y git nodejs \
&& rm -rf /var/lib/apt/lists/*
WORKDIR /app
COPY . .
RUN mvn clean && mvn package -T4C
FROM gitlab.micord.ru:5050/common/base/webbpm/webbpm-tomcat-cprocsp:8.0.15-jre17-webprofile
RUN \
rm -rf /usr/local/tomee/webapps/ROOT && \
echo "fias.enable=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.jbpm.hibernate_statistics.enabled=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.mode=production" >> /usr/local/tomee/conf/catalina.properties && \
echo "authentication.method=form" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.cache.hazelcast.hosts=127.0.0.1" >> /usr/local/tomee/conf/catalina.properties && \
echo "webbpm.cache.hazelcast.outbound_port_definitions=5801-5820" >> /usr/local/tomee/conf/catalina.properties && \
echo "gar.enable=false" >> /usr/local/tomee/conf/catalina.properties && \
echo "reset_password.mail.template.path=mail/reset_password.html" >> /usr/local/tomee/conf/catalina.properties && \
echo "security.password.regex=^(?=.*[a-zA-Z])(?=.*[0-9])[a-zA-Z0-9]+$" >> /usr/local/tomee/conf/catalina.properties && \
echo "bpmn.enable=false" >> /usr/local/tomee/conf/catalina.properties
COPY config/context.xml /usr/local/tomee/conf/
#COPY config/tomcat-users.xml /usr/local/tomee/conf/
COPY --from=build /app/backend/libs/ /usr/local/tomee/lib/
COPY --from=build /app/frontend/target/*.war /usr/local/tomee/webapps/ROOT.war
COPY --from=build /app/backend/target/*.war /usr/local/tomee/webapps/fl.war

BIN
backend/libs/JCP.jar Normal file

Binary file not shown.

View file

@ -23,6 +23,10 @@
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-api</artifactId>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-jackson</artifactId>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt-impl</artifactId>
@ -216,6 +220,10 @@
<groupId>org.bouncycastle</groupId>
<artifactId>bcprov-jdk15on</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.kafka</groupId>
<artifactId>spring-kafka</artifactId>
</dependency>
<dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcpkix-jdk15on</artifactId>

View file

@ -1,116 +1,85 @@
package ru.micord.ervu.kafka;
import java.time.Duration;
import java.util.HashMap;
import java.util.Map;
import org.apache.kafka.clients.CommonClientConfigs;
import org.apache.kafka.clients.consumer.ConsumerConfig;
import org.apache.kafka.clients.producer.ProducerConfig;
import org.apache.kafka.common.config.SaslConfigs;
import org.apache.kafka.common.serialization.BytesDeserializer;
import org.apache.kafka.common.serialization.StringDeserializer;
import org.apache.kafka.common.serialization.StringSerializer;
import org.apache.kafka.common.utils.Bytes;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.kafka.annotation.EnableKafka;
import org.springframework.kafka.config.ConcurrentKafkaListenerContainerFactory;
import org.springframework.kafka.core.ConsumerFactory;
import org.springframework.kafka.core.DefaultKafkaConsumerFactory;
import org.springframework.kafka.core.DefaultKafkaProducerFactory;
import org.springframework.kafka.core.KafkaTemplate;
import org.springframework.kafka.core.ProducerFactory;
import org.springframework.kafka.core.*;
import org.springframework.kafka.listener.ConcurrentMessageListenerContainer;
import org.springframework.kafka.requestreply.ReplyingKafkaTemplate;
import org.springframework.kafka.support.serializer.JsonSerializer;
//@Configuration
//@EnableKafka
import java.time.Duration;
import java.util.HashMap;
import java.util.Map;
@Configuration
@EnableKafka
public class ReplyingKafkaConfig {
@Value("${kafka.ervu.send.url}")
private String kafkaUrl;
@Value("${kafka.ervu.security.protocol}")
private String securityProtocol;
@Value("${kafka.ervu.doc.login.module}")
private String loginModule;
@Value("${kafka.ervu.username}")
private String username;
@Value("${kafka.ervu.password}")
private String password;
@Value("${kafka.ervu.sasl.mechanism}")
private String saslMechanism;
@Value("${ervu.kafka.bootstrap.servers}")
private String bootstrapServers;
@Value("${kafka.ervu.recruit.reply.topic}")
private String recruitReplyTopic;
@Value("${kafka.ervu.subpoena.extract.reply.topic}")
private String subpoenaExtractReplyTopic;
@Value("${kafka.ervu.registry.extract.reply.topic}")
private String registryExtractReplyTopic;
@Value("${ervu.kafka.reply.topic}")
private String replyTopic;
@Value("${kafka.ervu.group.id:1}")
@Value("${ervu.kafka.group.id}")
private String groupId;
@Value("${ervu-kafka.reply-timeout:10}")
@Value("${ervu.kafka.reply.timeout:30}")
private long replyTimeout;
@Bean
public ProducerFactory<String, Object> producerFactory() {
Map<String, Object> props = new HashMap<>();
props.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, this.kafkaUrl);
props.put(CommonClientConfigs.SECURITY_PROTOCOL_CONFIG, securityProtocol);
props.put(SaslConfigs.SASL_JAAS_CONFIG, loginModule + " required username=\""
+ username + "\" password=\"" + password + "\";");
props.put(SaslConfigs.SASL_MECHANISM, saslMechanism);
props.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class);
props.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, JsonSerializer.class);
return new DefaultKafkaProducerFactory<>(props);
public ProducerFactory<String, String> producerFactory() {
Map<String, Object> configProps = new HashMap<>();
configProps.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapServers);
configProps.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class);
configProps.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class);
return new DefaultKafkaProducerFactory<>(configProps);
}
@Bean
public KafkaTemplate<String, Object> kafkaTemplate() {
public KafkaTemplate<String, String> kafkaTemplate() {
return new KafkaTemplate<>(producerFactory());
}
@Bean
public ConsumerFactory<String, Bytes> consumerFactory() {
Map<String, Object> props = new HashMap<>();
props.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, this.kafkaUrl);
props.put(CommonClientConfigs.SECURITY_PROTOCOL_CONFIG, securityProtocol);
props.put(SaslConfigs.SASL_JAAS_CONFIG, loginModule + " required username=\""
+ username + "\" password=\"" + password + "\";");
props.put(SaslConfigs.SASL_MECHANISM, saslMechanism);
props.put(ConsumerConfig.GROUP_ID_CONFIG, groupId);
props.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
props.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, BytesDeserializer.class);
return new DefaultKafkaConsumerFactory<>(props);
public ConsumerFactory<String, String> consumerFactory() {
Map<String, Object> configProps = new HashMap<>();
configProps.put(ConsumerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapServers);
configProps.put(ConsumerConfig.GROUP_ID_CONFIG, groupId);
configProps.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
configProps.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
return new DefaultKafkaConsumerFactory<>(configProps);
}
@Bean
public ConcurrentKafkaListenerContainerFactory<String, Bytes> kafkaListenerContainerFactory() {
ConcurrentKafkaListenerContainerFactory<String, Bytes> factory =
new ConcurrentKafkaListenerContainerFactory<>();
public ConcurrentKafkaListenerContainerFactory<String, String> kafkaListenerContainerFactory() {
ConcurrentKafkaListenerContainerFactory<String, String> factory = new ConcurrentKafkaListenerContainerFactory<>();
factory.setConsumerFactory(consumerFactory());
return factory;
}
@Bean
public ConcurrentMessageListenerContainer<String, Bytes> replyContainer(
ConcurrentKafkaListenerContainerFactory<String, Bytes> factory) {
ConcurrentMessageListenerContainer<String, Bytes> container = factory.createContainer(
recruitReplyTopic, subpoenaExtractReplyTopic, registryExtractReplyTopic);
public ConcurrentMessageListenerContainer<String, String> replyContainer(
ConcurrentKafkaListenerContainerFactory<String, String> factory) {
ConcurrentMessageListenerContainer<String, String> container = factory.createContainer(
replyTopic);
container.getContainerProperties().setGroupId(groupId);
return container;
}
@Bean
public ReplyingKafkaTemplate<String, Object, Bytes> replyingKafkaTemplate(
ProducerFactory<String, Object> pf,
ConcurrentMessageListenerContainer<String, Bytes> container) {
ReplyingKafkaTemplate<String, Object, Bytes> replyingKafkaTemplate =
public ReplyingKafkaTemplate<String, String, String> replyingKafkaTemplate(
ProducerFactory<String, String> pf,
ConcurrentMessageListenerContainer<String, String> container) {
ReplyingKafkaTemplate<String, String, String> replyingKafkaTemplate =
new ReplyingKafkaTemplate<>(pf, container);
replyingKafkaTemplate.setCorrelationHeaderName("messageId");
replyingKafkaTemplate.setCorrelationHeaderName("messageID");
replyingKafkaTemplate.setDefaultReplyTimeout(Duration.ofSeconds(replyTimeout));
return replyingKafkaTemplate;
}

View file

@ -0,0 +1,43 @@
package ru.micord.ervu.kafka.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class Document implements Serializable {
private static final long serialVersionUID = 1L;
private String series;
private String number;
private String issueDate;
public String getSeries() {
return series;
}
public void setSeries(String series) {
this.series = series;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public String getIssueDate() {
return issueDate;
}
public void setIssueDate(String issueDate) {
this.issueDate = issueDate;
}
}

View file

@ -0,0 +1,33 @@
package ru.micord.ervu.kafka.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class ErrorData implements Serializable {
private static final long serialVersionUID = 1L;
private String code;
private String name;
public String getCode() {
return code;
}
public void setCode(String code) {
this.code = code;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}

View file

@ -0,0 +1,73 @@
package ru.micord.ervu.kafka.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class Person implements Serializable {
private static final long serialVersionUID = 1L;
private String lastName;
private String firstName;
private String middleName;
private String birthDate;
private String snils;
private Document document;
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getMiddleName() {
return middleName;
}
public void setMiddleName(String middleName) {
this.middleName = middleName;
}
public String getBirthDate() {
return birthDate;
}
public void setBirthDate(String birthDate) {
this.birthDate = birthDate;
}
public String getSnils() {
return snils;
}
public void setSnils(String snils) {
this.snils = snils;
}
public Document getDocument() {
return document;
}
public void setDocument(Document document) {
this.document = document;
}
}

View file

@ -0,0 +1,33 @@
package ru.micord.ervu.kafka.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class Response implements Serializable {
private static final long serialVersionUID = 1L;
private String ervuId;
private ErrorData errorData;
public String getErvuId() {
return ervuId;
}
public void setErvuId(String ervuId) {
this.ervuId = ervuId;
}
public ErrorData getErrorData() {
return errorData;
}
public void setErrorData(ErrorData errorData) {
this.errorData = errorData;
}
}

View file

@ -0,0 +1,8 @@
package ru.micord.ervu.kafka.service;
public interface ReplyingKafkaService {
String sendMessageAndGetReply(String requestTopic,
String requestReplyTopic,
String requestMessage);
}

View file

@ -0,0 +1,42 @@
package ru.micord.ervu.kafka.service.impl;
import java.util.Optional;
import java.util.concurrent.ExecutionException;
import org.apache.kafka.clients.consumer.ConsumerRecord;
import org.apache.kafka.clients.producer.ProducerRecord;
import org.apache.kafka.common.header.internals.RecordHeader;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.kafka.requestreply.ReplyingKafkaTemplate;
import org.springframework.kafka.requestreply.RequestReplyFuture;
import org.springframework.kafka.support.KafkaHeaders;
import org.springframework.stereotype.Service;
import ru.micord.ervu.kafka.service.ReplyingKafkaService;
/**
* @author Eduard Tihomirov
*/
@Service
public class ReplyingKafkaServiceImpl implements ReplyingKafkaService {
@Autowired
private ReplyingKafkaTemplate<String, String, String> replyingKafkaTemplate;
public String sendMessageAndGetReply(String requestTopic,
String requestReplyTopic,
String requestMessage) {
ProducerRecord<String, String> record = new ProducerRecord<>(requestTopic, requestMessage);
record.headers().add(new RecordHeader(KafkaHeaders.REPLY_TOPIC, requestReplyTopic.getBytes()));
RequestReplyFuture<String, String, String> replyFuture = replyingKafkaTemplate.sendAndReceive(
record);
try {
Optional<ConsumerRecord<String, String>> consumerRecord = Optional.ofNullable(replyFuture.get());
return consumerRecord.map(ConsumerRecord::value)
.orElseThrow(() -> new RuntimeException("Kafka return result is null."));
}
catch (InterruptedException | ExecutionException e) {
throw new RuntimeException("Failed to get kafka response.", e);
}
}
}

View file

@ -0,0 +1,62 @@
package ru.micord.ervu.security;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.web.AuthenticationEntryPoint;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import ru.micord.ervu.security.webbpm.jwt.filter.JwtAuthenticationFilter;
import ru.micord.ervu.security.webbpm.jwt.UnauthorizedEntryPoint;
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private JwtAuthenticationFilter jwtAuthenticationFilter;
@Override
protected void configure(HttpSecurity http) throws Exception {
httpConfigure(http);
http.addFilterBefore(jwtAuthenticationFilter, UsernamePasswordAuthenticationFilter.class);
}
protected void httpConfigure(HttpSecurity httpSecurity) throws Exception {
String[] permitAll = {"/esia/url", "/esia/auth", "esia/refresh"};
httpSecurity.authorizeRequests()
.antMatchers(permitAll).permitAll()
.antMatchers("/**").authenticated()
.and()
.csrf().disable()
.exceptionHandling().authenticationEntryPoint(entryPoint())
.and()
.sessionManagement()
.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
}
public AuthenticationEntryPoint entryPoint() {
return new UnauthorizedEntryPoint();
}
@Bean
@Override
public AuthenticationManager authenticationManagerBean() throws Exception {
return super.authenticationManagerBean();
}
@Bean
public JwtAuthenticationFilter jwtAuthenticationFilter() throws Exception {
JwtAuthenticationFilter jwtAuthenticationFilter = new JwtAuthenticationFilter("/**",
entryPoint()
);
jwtAuthenticationFilter.setAuthenticationManager(authenticationManagerBean());
return jwtAuthenticationFilter;
}
}

View file

@ -0,0 +1,89 @@
package ru.micord.ervu.security.esia.config;
import java.util.Arrays;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
/**
* @author Eduard Tihomirov
*/
@Component
public class EsiaConfig {
@Value("${esia.scopes}")
private String esiaScopes;
@Value("${esia.base.uri}")
private String esiaBaseUri;
@Value("${esia.client.id}")
private String clientId;
@Value("${esia.redirect.url}")
private String redirectUrl;
@Value("${sign.url}")
private String signUrl;
@Value("${client.cert.hash}")
private String clientCertHash;
@Value("${esia.request.timeout:60}")
private long requestTimeout;
@Value("${esia.connection.timeout:30}")
private long connectionTimeout;
@Value("${esia.logout.url:idp/ext/Logout}")
private String esiaLogoutUrl;
@Value("${esia.code.url:aas/oauth2/v3/te}")
private String esiaCodeUrl;
@Value("${esia.token.url:aas/oauth2/v3/te}")
private String esiaTokenUrl;
public String getEsiaScopes() {
String[] scopeItems = esiaScopes.split(",");
return String.join(" ", Arrays.stream(scopeItems).map(String::trim).toArray(String[]::new));
}
public String getClientId() {
return clientId;
}
public String getRedirectUrl() {
return redirectUrl;
}
public String getEsiaBaseUri() {
return esiaBaseUri;
}
public String getSignUrl() {
return signUrl;
}
public String getClientCertHash() {return clientCertHash;}
public long getRequestTimeout() {
return requestTimeout;
}
public long getConnectionTimeout() {
return connectionTimeout;
}
public String getEsiaLogoutUrl() {
return esiaLogoutUrl;
}
public String getEsiaCodeUrl() {
return esiaCodeUrl;
}
public String getEsiaTokenUrl() {
return esiaTokenUrl;
}
}

View file

@ -0,0 +1,92 @@
package ru.micord.ervu.security.esia.controller;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import ru.micord.ervu.security.esia.model.PersonDataModel;
import ru.micord.ervu.security.esia.model.PersonModel;
import ru.micord.ervu.security.esia.service.EsiaAuthService;
import ru.micord.ervu.security.esia.service.PersonalDataService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
/**
* @author Eduard Tihomirov
*/
@RestController
public class EsiaController {
@Autowired
private EsiaAuthService esiaAuthService;
@Autowired
private PersonalDataService personalDataService;
@RequestMapping(value = "/esia/url")
public String getEsiaUrl() {
return esiaAuthService.generateAuthCodeUrl();
}
@RequestMapping(value = "/esia/auth", params = "code", method = RequestMethod.GET)
public boolean esiaAuth(@RequestParam("code") String code, HttpServletRequest request, HttpServletResponse response) {
return esiaAuthService.getEsiaTokensByCode(code, request, response);
}
@RequestMapping(value = "/esia/refresh")
public void refreshToken(HttpServletRequest request, HttpServletResponse response) {
esiaAuthService.getEsiaTokensByRefreshToken(request, response);
}
@RequestMapping(value = "/esia/person")
public PersonDataModel getPersonModel(HttpServletRequest request) {
String accessToken = null;
Cookie[] cookies = request.getCookies();
if (cookies != null) {
for (Cookie cookie : cookies) {
if (cookie.getName().equals("access_token")) {
accessToken = cookie.getValue();
}
}
}
if (accessToken == null) {
return null;
}
PersonModel personModel = personalDataService.getPersonModel(accessToken);
PersonDataModel personDataModel = new PersonDataModel();
personDataModel.birthDate = personModel.getBirthDate().toString();
personDataModel.fullname = personModel.getLastName() + " " + personModel.getFirstName() + " "
+ personModel.getMiddleName();
personDataModel.snils = personModel.getSnils();
personDataModel.seriesAndNumber =
personModel.getPassportModel().getSeries() + " " + personModel.getPassportModel()
.getNumber();
personDataModel.issueDate = personModel.getPassportModel().getIssueDate().toString();
personDataModel.issuedBy = personModel.getPassportModel().getIssuedBy();
personDataModel.issueId = personModel.getPassportModel().getIssueId();
return personDataModel;
}
@RequestMapping(value = "/esia/userfullname")
public String getUserFullname(HttpServletRequest request) {
String accessToken = null;
Cookie[] cookies = request.getCookies();
if (cookies != null) {
for (Cookie cookie : cookies) {
if (cookie.getName().equals("access_token")) {
accessToken = cookie.getValue();
}
}
}
if (accessToken == null) {
return null;
}
PersonModel personModel = personalDataService.getPersonModel(accessToken);
return personModel.getLastName() + " " + personModel.getFirstName().charAt(0) + ". " + personModel.getMiddleName().charAt(0) + ".";
}
@RequestMapping(value = "/esia/logout")
public String logout(HttpServletRequest request, HttpServletResponse response) {
return esiaAuthService.logout(request, response);
}
}

View file

@ -0,0 +1,97 @@
package ru.micord.ervu.security.esia.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class EsiaAccessToken implements Serializable {
private static final long serialVersionUID = -8580344482588383113L;
private Long exp;
private String scope;
private String iss;
private Long nbf;
@JsonProperty("urn:esia:sid")
private String sid;
@JsonProperty("urn:esia:sbj_id")
private String sbj_id;
private String client_id;
private Long iat;
public Long getExp() {
return exp;
}
public void setExp(Long exp) {
this.exp = exp;
}
public String getScope() {
return scope;
}
public void setScope(String scope) {
this.scope = scope;
}
public String getIss() {
return iss;
}
public void setIss(String iss) {
this.iss = iss;
}
public Long getNbf() {
return nbf;
}
public void setNbf(Long nbf) {
this.nbf = nbf;
}
public String getSid() {
return sid;
}
public void setSid(String sid) {
this.sid = sid;
}
public String getSbj_id() {
return sbj_id;
}
public void setSbj_id(String sbj_id) {
this.sbj_id = sbj_id;
}
public String getClient_id() {
return client_id;
}
public void setClient_id(String client_id) {
this.client_id = client_id;
}
public Long getIat() {
return iat;
}
public void setIat(Long iat) {
this.iat = iat;
}
}

View file

@ -0,0 +1,94 @@
package ru.micord.ervu.security.esia.model;
import java.io.Serializable;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class EsiaTokenResponse implements Serializable {
private static final long serialVersionUID = 7655328287602576975L;
private String id_token;
private String access_token;
private String refresh_token;
private String state;
private String token_type;
private Long expires_in;
private String error;
private String error_description;
public String getId_token() {
return id_token;
}
public void setId_token(String id_token) {
this.id_token = id_token;
}
public String getAccess_token() {
return access_token;
}
public void setAccess_token(String access_token) {
this.access_token = access_token;
}
public String getRefresh_token() {
return refresh_token;
}
public void setRefresh_token(String refresh_token) {
this.refresh_token = refresh_token;
}
public String getState() {
return state;
}
public void setState(String state) {
this.state = state;
}
public String getToken_type() {
return token_type;
}
public void setToken_type(String token_type) {
this.token_type = token_type;
}
public Long getExpires_in() {
return expires_in;
}
public void setExpires_in(Long expires_in) {
this.expires_in = expires_in;
}
public String getError() {
return error;
}
public void setError(String error) {
this.error = error;
}
public String getError_description() {
return error_description;
}
public void setError_description(String error_description) {
this.error_description = error_description;
}
}

View file

@ -0,0 +1,42 @@
package ru.micord.ervu.security.esia.model;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;
/**
* Данные HTML-формы для POST с Content-Type=application/x-www-form-urlencoded.
*/
public class FormUrlencoded {
// todo: private final Map<String, List<String>> ...
private final Map<String, String> formData = new HashMap<>();
/**
* Устанавливает параметр в форму.
*/
public FormUrlencoded setParameter(String name, String value) {
if (name != null) formData.put(name, value);
return this;
}
/**
* Собирает из формы и возвращает строку в виде application/x-www-form-urlencoded.
*/
public String toFormUrlencodedString() {
final StringBuilder sb = new StringBuilder();
formData.forEach((key, value) -> {
if (key != null) key = URLEncoder.encode(key, StandardCharsets.UTF_8);
if (value != null) value = URLEncoder.encode(value, StandardCharsets.UTF_8);
if (sb.length() > 0) sb.append("&");
sb.append(key).append("=").append(value);
});
return sb.toString();
}
@Override
public String toString() {
return toFormUrlencodedString();
}
}

View file

@ -0,0 +1,67 @@
package ru.micord.ervu.security.esia.model;
import java.io.Serializable;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class PassportModel implements Serializable {
public static final long serialVersionUID = 1L;
private String series;
private String number;
@JsonFormat(pattern = "dd.MM.yyyy")
private Date issueDate;
private String issueId;
private String issuedBy;
public String getSeries() {
return series;
}
public void setSeries(String series) {
this.series = series;
}
public String getNumber() {
return number;
}
public void setNumber(String number) {
this.number = number;
}
public Date getIssueDate() {
return issueDate;
}
public void setIssueDate(Date issueDate) {
this.issueDate = issueDate;
}
public String getIssueId() {
return issueId;
}
public void setIssueId(String issueId) {
this.issueId = issueId;
}
public String getIssuedBy() {
return issuedBy;
}
public void setIssuedBy(String issuedBy) {
this.issuedBy = issuedBy;
}
}

View file

@ -0,0 +1,24 @@
package ru.micord.ervu.security.esia.model;
import ru.cg.webbpm.modules.webkit.annotations.Model;
/**
* @author Eduard Tihomirov
*/
@Model
public class PersonDataModel {
public String fullname;
public String birthDate;
public String snils;
public String seriesAndNumber;
public String issueDate;
public String issueId;
public String issuedBy;
}

View file

@ -0,0 +1,105 @@
package ru.micord.ervu.security.esia.model;
import java.io.Serializable;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
/**
* @author Eduard Tihomirov
*/
@JsonIgnoreProperties(ignoreUnknown = true)
public class PersonModel implements Serializable {
private static final long serialVersionUID = 1L;
private String prnsId;
private String rIdDoc;
private String lastName;
private String firstName;
private String middleName;
@JsonFormat(pattern = "dd.MM.yyyy")
private Date birthDate;
private String snils;
private PassportModel passportModel;
public String getPrnsId() {
return prnsId;
}
public void setPrnsId(String prnsId) {
this.prnsId = prnsId;
}
public String getrIdDoc() {
return rIdDoc;
}
public void setrIdDoc(String rIdDoc) {
this.rIdDoc = rIdDoc;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getMiddleName() {
return middleName;
}
public void setMiddleName(String middleName) {
this.middleName = middleName;
}
public Date getBirthDate() {
return birthDate;
}
public void setBirthDate(Date birthDate) {
this.birthDate = birthDate;
}
public String getSnils() {
return snils;
}
public void setSnils(String snils) {
this.snils = snils;
}
public PassportModel getPassportModel() {
return passportModel;
}
public void setPassportModel(PassportModel passportModel) {
this.passportModel = passportModel;
}
@Override
public String toString() {
return firstName + " " + middleName + " " + lastName + " " + birthDate + " " + snils + " "
+ passportModel.getNumber() + " " + passportModel.getSeries() + " "
+ passportModel.getIssuedBy() + " " + passportModel.getIssueId() + " "
+ passportModel.getIssueDate();
}
}

View file

@ -0,0 +1,424 @@
package ru.micord.ervu.security.esia.service;
import java.io.UnsupportedEncodingException;
import java.net.URI;
import java.net.URL;
import java.net.URLEncoder;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.nio.charset.StandardCharsets;
import java.time.Duration;
import java.time.ZonedDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Base64;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.UUID;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.beans.factory.annotation.Value;
import ru.micord.ervu.kafka.model.Document;
import ru.micord.ervu.kafka.model.Person;
import ru.micord.ervu.kafka.model.Response;
import ru.micord.ervu.kafka.service.ReplyingKafkaService;
import ru.micord.ervu.security.esia.config.EsiaConfig;
import ru.micord.ervu.security.esia.model.FormUrlencoded;
import ru.micord.ervu.security.esia.model.EsiaAccessToken;
import ru.micord.ervu.security.esia.model.EsiaTokenResponse;
import ru.micord.ervu.security.esia.model.PersonModel;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpHeaders;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Service;
import ru.micord.ervu.security.webbpm.jwt.service.JwtTokenService;
import ru.micord.ervu.security.webbpm.jwt.model.Token;
/**
* @author Eduard Tihomirov
*/
@Service
public class EsiaAuthService {
@Value("${cookie.path:#{null}}")
private String path;
@Autowired
private ObjectMapper objectMapper;
@Autowired
private EsiaConfig esiaConfig;
@Autowired
private JwtTokenService jwtTokenService;
@Autowired
private ReplyingKafkaService replyingKafkaService;
@Autowired
private PersonalDataService personalDataService;
@Value("${ervu.kafka.reply.topic}")
private String requestReplyTopic;
@Value("${ervu.kafka.request.topic}")
private String requestTopic;
public String generateAuthCodeUrl() {
try {
String clientId = esiaConfig.getClientId();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss xx");
ZonedDateTime dt = ZonedDateTime.now();
String timestamp = dt.format(formatter);
String state = UUID.randomUUID().toString();
String redirectUrl = esiaConfig.getRedirectUrl();
String redirectUrlEncoded = redirectUrl.replaceAll(":", "%3A")
.replaceAll("/", "%2F");
String scope = esiaConfig.getEsiaScopes();
Map<String, String> parameters = new LinkedHashMap<String, String>();
parameters.put("client_id", clientId);
parameters.put("scope", scope);
parameters.put("timestamp", timestamp);
parameters.put("state", state);
parameters.put("redirect_uri", esiaConfig.getRedirectUrl());
String clientSecret = signMap(parameters);
String responseType = "code";
String authUrl = esiaConfig.getEsiaBaseUri() + esiaConfig.getEsiaCodeUrl();
URL url = new URL(authUrl);
Map<String, String> params = mapOf("scope", scope,
"timestamp", urlEncode(timestamp),
"state", state,
"client_id", clientId,
"client_secret", clientSecret,
"response_type", responseType,
"redirect_uri", redirectUrlEncoded,
"client_certificate_hash", esiaConfig.getClientCertHash());
return makeRequest(url, params);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private static Map<String, String> mapOf(String... params) {
if (params.length % 2 != 0) {
throw new IllegalArgumentException("Invalid params count");
}
Map<String, String> map = new LinkedHashMap<>(params.length / 2);
for (int i = 0; i < params.length / 2; i++) {
map.put(params[i * 2], params[i * 2 + 1]);
}
return map;
}
private static String urlEncode(String s) {
try {
return URLEncoder.encode(s, "UTF-8")
.replace("+", "%20");
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
}
private static String makeRequest(URL url, Map<String, String> params) {
StringBuilder uriBuilder = new StringBuilder(url.toString());
uriBuilder.append('?');
for (Map.Entry<String, String> node : params.entrySet()) {
uriBuilder.append(node.getKey()).append('=').append(node.getValue()).append("&");
}
return uriBuilder.toString();
}
public boolean getEsiaTokensByCode(String esiaAuthCode, HttpServletRequest request, HttpServletResponse response) {
try {
String clientId = esiaConfig.getClientId();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss xx");
ZonedDateTime dt = ZonedDateTime.now();
String timestamp = dt.format(formatter);
String state = UUID.randomUUID().toString();
String redirectUrl = esiaConfig.getRedirectUrl();
String scope = esiaConfig.getEsiaScopes();
Map<String, String> parameters = new LinkedHashMap<String, String>();
parameters.put("client_id", clientId);
parameters.put("scope", scope);
parameters.put("timestamp", timestamp);
parameters.put("state", state);
parameters.put("redirect_uri", redirectUrl);
parameters.put("code", esiaAuthCode);
String clientSecret = signMap(parameters);
String authUrl = esiaConfig.getEsiaBaseUri() + esiaConfig.getEsiaTokenUrl();
String postBody = new FormUrlencoded()
.setParameter("client_id", clientId)
.setParameter("code", esiaAuthCode)
.setParameter("grant_type", "authorization_code")
.setParameter("client_secret", clientSecret)
.setParameter("state", state)
.setParameter("redirect_uri", redirectUrl)
.setParameter("scope", scope)
.setParameter("timestamp", timestamp)
.setParameter("token_type", "Bearer")
.setParameter("client_certificate_hash", esiaConfig.getClientCertHash())
.toFormUrlencodedString();
HttpRequest postReq = HttpRequest.newBuilder(URI.create(authUrl))
.header(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded")
.POST(HttpRequest.BodyPublishers.ofString(postBody))
.timeout(Duration.ofSeconds(esiaConfig.getRequestTimeout()))
.build();
HttpResponse<String> postResp = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(esiaConfig.getConnectionTimeout()))
.build()
.send(postReq, HttpResponse.BodyHandlers.ofString());
String responseString = postResp.body();
EsiaTokenResponse tokenResponse = objectMapper.readValue(responseString, EsiaTokenResponse.class);
if (tokenResponse != null && tokenResponse.getError() != null) {
throw new RuntimeException(tokenResponse.getError_description());
}
String cookiePath = null;
if (path != null) {
cookiePath = path;
}
else {
cookiePath = request.getContextPath();
}
String accessToken = tokenResponse.getAccess_token();
Cookie cookie = new Cookie("access_token", accessToken);
cookie.setHttpOnly(true);
cookie.setPath(cookiePath);
response.addCookie(cookie);
String refreshToken = tokenResponse.getRefresh_token();
Cookie cookieRefresh = new Cookie("refresh_token", refreshToken);
cookieRefresh.setHttpOnly(true);
cookieRefresh.setPath(cookiePath);
response.addCookie(cookieRefresh);
byte[] decodedBytes = Base64.getDecoder()
.decode(
accessToken.substring(accessToken.indexOf('.') + 1, accessToken.lastIndexOf('.')));
String decodedString = new String(decodedBytes);
EsiaAccessToken esiaAccessToken = objectMapper.readValue(decodedString, EsiaAccessToken.class);
String ervuId = getErvuId(accessToken);
Token token = jwtTokenService.createAccessToken(esiaAccessToken.getSbj_id(), tokenResponse.getExpires_in(), ervuId);
Cookie authToken = new Cookie("auth_token", token.getValue());
authToken.setPath(cookiePath);
authToken.setHttpOnly(true);
response.addCookie(authToken);
SecurityContextHolder.getContext()
.setAuthentication(
new UsernamePasswordAuthenticationToken(esiaAccessToken.getSbj_id(), null));
Cookie isAuth = new Cookie("is_auth", "true");
isAuth.setPath(cookiePath);
isAuth.setMaxAge(tokenResponse.getExpires_in().intValue());
response.addCookie(isAuth);
return true;
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
public void getEsiaTokensByRefreshToken(HttpServletRequest request, HttpServletResponse response) {
try {
String refreshToken = null;
Cookie[] cookies = request.getCookies();
if (cookies != null) {
for (Cookie cookie : cookies) {
if (cookie.getName().equals("refresh_token")) {
refreshToken = cookie.getValue();
}
}
}
String clientId = esiaConfig.getClientId();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss xx");
ZonedDateTime dt = ZonedDateTime.now();
String timestamp = dt.format(formatter);
String state = UUID.randomUUID().toString();
String redirectUrl = esiaConfig.getRedirectUrl();
Map<String, String> parameters = new LinkedHashMap<String, String>();
parameters.put("client_id", clientId);
parameters.put("scope", esiaConfig.getEsiaScopes());
parameters.put("timestamp", timestamp);
parameters.put("state", state);
parameters.put("redirect_uri", esiaConfig.getRedirectUrl());
parameters.put("refresh_token", refreshToken);
String clientSecret = signMap(parameters);
String authUrl = esiaConfig.getEsiaBaseUri() + esiaConfig.getEsiaTokenUrl();
String postBody = new FormUrlencoded()
.setParameter("client_id", clientId)
.setParameter("refresh_token", refreshToken)
.setParameter("grant_type", "refresh_token")
.setParameter("client_secret", clientSecret)
.setParameter("state", state)
.setParameter("redirect_uri", redirectUrl)
.setParameter("scope", esiaConfig.getEsiaScopes())
.setParameter("timestamp", timestamp)
.setParameter("token_type", "Bearer")
.setParameter("client_certificate_hash", esiaConfig.getClientCertHash())
.toFormUrlencodedString();
HttpRequest postReq = HttpRequest.newBuilder(URI.create(authUrl))
.header(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded")
.POST(HttpRequest.BodyPublishers.ofString(postBody))
.timeout(Duration.ofSeconds(esiaConfig.getRequestTimeout()))
.build();
HttpResponse<String> postResp = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(esiaConfig.getConnectionTimeout()))
.build()
.send(postReq, HttpResponse.BodyHandlers.ofString());
String responseString = postResp.body();
EsiaTokenResponse tokenResponse = objectMapper.readValue(responseString, EsiaTokenResponse.class);
if (tokenResponse != null && tokenResponse.getError() != null) {
throw new RuntimeException(tokenResponse.getError_description());
}
String accessToken = tokenResponse.getAccess_token();
Cookie cookie = new Cookie("access_token", accessToken);
cookie.setHttpOnly(true);
String cookiePath = null;
if (path != null) {
cookiePath = path;
}
else {
cookiePath = request.getContextPath();
}
cookie.setPath(cookiePath);
response.addCookie(cookie);
String newRefreshToken = tokenResponse.getRefresh_token();
Cookie cookieRefresh = new Cookie("refresh_token", newRefreshToken);
cookieRefresh.setHttpOnly(true);
cookieRefresh.setPath(cookiePath);
response.addCookie(cookieRefresh);
byte[] decodedBytes = Base64.getDecoder()
.decode(
accessToken.substring(accessToken.indexOf('.') + 1, accessToken.lastIndexOf('.')));
String decodedString = new String(decodedBytes);
EsiaAccessToken esiaAccessToken = objectMapper.readValue(decodedString, EsiaAccessToken.class);
String ervuId = getErvuId(accessToken);
Token token = jwtTokenService.createAccessToken(esiaAccessToken.getSbj_id(), tokenResponse.getExpires_in(), ervuId);
Cookie authToken = new Cookie("auth_token", token.getValue());
authToken.setPath(cookiePath);
authToken.setHttpOnly(true);
response.addCookie(authToken);
SecurityContextHolder.getContext()
.setAuthentication(
new UsernamePasswordAuthenticationToken(esiaAccessToken.getSbj_id(), null));
Cookie isAuth = new Cookie("is_auth", "true");
isAuth.setMaxAge(tokenResponse.getExpires_in().intValue());
isAuth.setPath(cookiePath);
response.addCookie(isAuth);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private String signMap(Map<String, String> paramsToSign) {
try {
StringBuilder toSign = new StringBuilder();
for (String s : paramsToSign.values()) {
toSign.append(s);
}
String requestBody = toSign.toString();
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create(esiaConfig.getSignUrl()))
.header("Content-Type", "text/plain")
.POST(HttpRequest.BodyPublishers.ofString(requestBody, StandardCharsets.UTF_8))
.build();
HttpResponse<String> response = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(esiaConfig.getConnectionTimeout()))
.build()
.send(request, HttpResponse.BodyHandlers.ofString());
errorHandler(response);
return response.body();
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private void errorHandler(HttpResponse httpResponse) {
if (httpResponse.statusCode() != 200) {
throw new RuntimeException(httpResponse.statusCode() + " " + httpResponse.body());
}
}
public String logout(HttpServletRequest request, HttpServletResponse response) {
try {
Cookie[] cookies = request.getCookies();
if (cookies != null)
for (Cookie cookie : cookies) {
if (cookie.getName().equals("auth_token") || cookie.getName().equals("refresh_token")
|| cookie.getName().equals("access_token") || cookie.getName().equals("is_auth")) {
cookie.setValue("");
cookie.setMaxAge(0);
response.addCookie(cookie);
}
}
String logoutUrl = esiaConfig.getEsiaBaseUri() + esiaConfig.getEsiaLogoutUrl();
String redirectUrl = esiaConfig.getRedirectUrl();
URL url = new URL(logoutUrl);
Map<String, String> params = mapOf(
"client_id", esiaConfig.getClientId(),
"redirect_url", redirectUrl);
return makeRequest(url, params);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
public String getErvuId(String accessToken) {
try {
PersonModel personModel = personalDataService.getPersonModel(accessToken);
Person person = copyToPerson(personModel);
String kafkaResponse = replyingKafkaService.sendMessageAndGetReply(requestTopic,
requestReplyTopic, objectMapper.writeValueAsString(person)
);
Response response = objectMapper.readValue(kafkaResponse, Response.class);
if (response.getErrorData() != null) {
throw new RuntimeException(
"Error code = " + response.getErrorData().getCode() + ", error name = "
+ response.getErrorData().getName());
}
else {
return response.getErvuId();
}
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private Person copyToPerson(PersonModel personModel) {
Person person = new Person();
person.setBirthDate(personModel.getBirthDate().toString());
person.setFirstName(personModel.getFirstName());
person.setLastName(personModel.getLastName());
person.setSnils(personModel.getSnils());
person.setMiddleName(personModel.getMiddleName());
Document document = new Document();
document.setNumber(personModel.getPassportModel().getNumber());
document.setSeries(personModel.getPassportModel().getSeries());
document.setIssueDate(personModel.getPassportModel().getIssueDate().toString());
return person;
}
}

View file

@ -0,0 +1,91 @@
package ru.micord.ervu.security.esia.service;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.time.Duration;
import java.util.Base64;
import com.fasterxml.jackson.databind.ObjectMapper;
import ru.micord.ervu.security.esia.config.EsiaConfig;
import ru.micord.ervu.security.esia.model.EsiaAccessToken;
import ru.micord.ervu.security.esia.model.PassportModel;
import ru.micord.ervu.security.esia.model.PersonModel;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpHeaders;
import org.springframework.stereotype.Service;
/**
* @author Eduard Tihomirov
*/
@Service
public class EsiaPersonalDataService implements PersonalDataService {
@Autowired
private EsiaConfig esiaConfig;
@Autowired
private ObjectMapper objectMapper;
@Override
public PersonModel getPersonModel(String accessToken) {
try {
byte[] decodedBytes = Base64.getDecoder()
.decode(
accessToken.substring(accessToken.indexOf('.') + 1, accessToken.lastIndexOf('.')));
String decodedString = new String(decodedBytes);
EsiaAccessToken esiaAccessToken = objectMapper.readValue(decodedString, EsiaAccessToken.class);
String prnsId = esiaAccessToken.getSbj_id();
PersonModel personModel = getPersonData(prnsId, accessToken);
personModel.setPassportModel(
getPassportModel(prnsId, accessToken, personModel.getrIdDoc()));
personModel.setPrnsId(prnsId);
return personModel;
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private PassportModel getPassportModel(String prsnId, String accessToken, String docId) {
try {
String url = esiaConfig.getEsiaBaseUri() + "rs/prns/" + prsnId;
HttpRequest getReqDoc = HttpRequest.newBuilder(URI.create(url + "/docs/" + docId))
.header(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded")
.header("Authorization", "Bearer ".concat(accessToken))
.GET()
.timeout(Duration.ofSeconds(esiaConfig.getRequestTimeout()))
.build();
HttpResponse<String> getRespDoc = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(esiaConfig.getConnectionTimeout()))
.build()
.send(getReqDoc, HttpResponse.BodyHandlers.ofString());
return objectMapper.readValue(getRespDoc.body(), PassportModel.class);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
private PersonModel getPersonData(String prsnId, String accessToken) {
try {
String url = esiaConfig.getEsiaBaseUri() + "rs/prns/";
HttpRequest getReq = HttpRequest.newBuilder(URI.create(url + prsnId))
.header(HttpHeaders.CONTENT_TYPE, "application/x-www-form-urlencoded")
.header("Authorization", "Bearer ".concat(accessToken))
.GET()
.timeout(Duration.ofSeconds(esiaConfig.getRequestTimeout()))
.build();
HttpResponse<String> getResp = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(esiaConfig.getConnectionTimeout()))
.build()
.send(getReq, HttpResponse.BodyHandlers.ofString());
return objectMapper.readValue(getResp.body(), PersonModel.class);
}
catch (Exception e) {
throw new RuntimeException(e);
}
}
}

View file

@ -0,0 +1,11 @@
package ru.micord.ervu.security.esia.service;
import ru.micord.ervu.security.esia.model.PersonModel;
/**
* @author Eduard Tihomirov
*/
public interface PersonalDataService {
PersonModel getPersonModel(String accessToken);
}

View file

@ -0,0 +1,77 @@
package ru.micord.ervu.security.webbpm.jwt;
import java.util.Collection;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.SpringSecurityCoreVersion;
/**
* @author zamaliev
*/
public class JwtAuthentication implements Authentication {
private static final long serialVersionUID = SpringSecurityCoreVersion.SERIAL_VERSION_UID;
private final String userAccountId;
private final Authentication authentication;
private final String token;
public JwtAuthentication(Authentication authentication, String userAccountId, String token) {
this.userAccountId = userAccountId;
this.authentication = authentication;
this.token = token;
}
public JwtAuthentication(Authentication authentication, String userAccountId) {
this(authentication, userAccountId, null);
}
public String getUserAccountId() {
return userAccountId;
}
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return authentication.getAuthorities();
}
@Override
public Object getCredentials() {
return authentication.getCredentials();
}
@Override
public Object getDetails() {
return authentication.getDetails();
}
@Override
public Object getPrincipal() {
return authentication.getPrincipal();
}
@Override
public boolean isAuthenticated() {
if (authentication == null) {
return false;
}
else {
return authentication.isAuthenticated();
}
}
@Override
public void setAuthenticated(boolean isAuthenticated) throws IllegalArgumentException {
authentication.setAuthenticated(isAuthenticated);
}
@Override
public String getName() {
return authentication.getName();
}
public String getToken() {
return this.token;
}
}

View file

@ -0,0 +1,57 @@
package ru.micord.ervu.security.webbpm.jwt;
import io.jsonwebtoken.ExpiredJwtException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.CredentialsExpiredException;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.stereotype.Component;
import ru.micord.ervu.security.webbpm.jwt.model.Token;
import ru.micord.ervu.security.webbpm.jwt.service.JwtTokenService;
@Component
public class JwtAuthenticationProvider implements AuthenticationProvider {
private final JwtTokenService jwtTokenService;
@Autowired
public JwtAuthenticationProvider(JwtTokenService jwtTokenService) {
this.jwtTokenService = jwtTokenService;
}
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
JwtAuthentication jwtAuthentication = (JwtAuthentication) authentication;
String tokenStr = jwtAuthentication.getToken();
Token token;
try {
token = jwtTokenService.getToken(tokenStr);
}
catch (ExpiredJwtException e) {
throw new CredentialsExpiredException("The access token is expired and not valid anymore.",
e
);
}
catch (Exception e) {
throw new BadCredentialsException("Authentication Failed.", e);
}
if (!jwtTokenService.isValid(token)) {
throw new BadCredentialsException("Auth token is not valid for user " + token.getUserAccountId());
}
UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken =
new UsernamePasswordAuthenticationToken(token.getUserAccountId(), null);
return new JwtAuthentication(usernamePasswordAuthenticationToken, token.getUserAccountId());
}
@Override
public boolean supports(Class<?> aClass) {
return JwtAuthentication.class.isAssignableFrom(aClass);
}
}

View file

@ -0,0 +1,29 @@
package ru.micord.ervu.security.webbpm.jwt;
import java.io.IOException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.web.AuthenticationEntryPoint;
/**
* {@link AuthenticationEntryPoint} that rejects all requests with an unauthorized error message.
*/
public class UnauthorizedEntryPoint implements AuthenticationEntryPoint {
@Override
public void commence(HttpServletRequest request, HttpServletResponse response,
AuthenticationException exception) throws IOException {
//for correct work with cross domain request
if ("OPTIONS".equals(request.getMethod())) {
response.setStatus(HttpServletResponse.SC_OK);
}
else {
response.sendError(HttpServletResponse.SC_UNAUTHORIZED,
"Unauthorized: Authentication token was either missing or invalid."
);
}
}
}

View file

@ -0,0 +1,84 @@
package ru.micord.ervu.security.webbpm.jwt.filter;
import java.io.IOException;
import java.lang.invoke.MethodHandles;
import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.authentication.CredentialsExpiredException;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.web.AuthenticationEntryPoint;
import org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter;
import ru.micord.ervu.security.webbpm.jwt.JwtAuthentication;
/**
* @author Flyur Karimov
*/
public class JwtAuthenticationFilter extends AbstractAuthenticationProcessingFilter {
private static final Logger LOGGER = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
private final AuthenticationEntryPoint entryPoint;
public JwtAuthenticationFilter(String securityPath, AuthenticationEntryPoint entryPoint) {
super(securityPath);
this.entryPoint = entryPoint;
}
@Override
public Authentication attemptAuthentication(HttpServletRequest httpServletRequest,
HttpServletResponse httpServletResponse) throws AuthenticationException {
String token = extractAuthTokenFromRequest(httpServletRequest);
Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
if (authentication == null) {
authentication = new JwtAuthentication(null, null, token);
}
try {
authentication = getAuthenticationManager().authenticate(authentication);
}
catch (CredentialsExpiredException e) {
httpServletResponse.setStatus(401);
LOGGER.warn(e.getMessage());
}
return authentication;
}
@Override
protected boolean requiresAuthentication(HttpServletRequest request, HttpServletResponse response) {
return extractAuthTokenFromRequest(request) != null;
}
@Override
protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response,
FilterChain chain, Authentication authentication) throws IOException, ServletException {
SecurityContextHolder.getContext().setAuthentication(authentication);
chain.doFilter(request, response);
}
@Override
protected void unsuccessfulAuthentication(HttpServletRequest request, HttpServletResponse response,
AuthenticationException exception) throws IOException, ServletException {
LOGGER.error("Jwt unsuccessful authentication exception", exception);
SecurityContextHolder.clearContext();
entryPoint.commence(request, response, exception);
}
public String extractAuthTokenFromRequest(HttpServletRequest httpRequest) {
String token = null;
Cookie[] cookies = httpRequest.getCookies();
if (cookies != null) {
for (Cookie cookie : cookies) {
if (cookie.getName().equals("auth_token")) {
token = cookie.getValue();
}
}
}
return token;
}
}

View file

@ -0,0 +1,37 @@
package ru.micord.ervu.security.webbpm.jwt.model;
import java.util.Date;
public class Token {
private final String userAccountId;
private final String issuer;
private final Date expirationDate;
private final String value;
public Token(String userAccountId, String issuer, Date expirationDate, String value) {
this.userAccountId = userAccountId;
this.issuer = issuer;
this.expirationDate = expirationDate;
this.value = value;
}
public String getUserAccountId() {
return userAccountId;
}
public String getIssuer() {
return issuer;
}
public Date getExpirationDate() {
return expirationDate;
}
public boolean isExpired() {
return expirationDate.before(new Date());
}
public String getValue() {
return value;
}
}

View file

@ -0,0 +1,75 @@
package ru.micord.ervu.security.webbpm.jwt.service;
import java.lang.invoke.MethodHandles;
import java.util.Base64;
import java.util.Date;
import javax.crypto.SecretKey;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.security.Keys;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import ru.micord.ervu.security.webbpm.jwt.model.Token;
import ru.cg.webbpm.modules.resources.api.ResourceMetadataUtils;
/**
* @author Flyur Karimov
*/
@Component
public class JwtTokenService {
private static final Logger LOGGER = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass());
@Value("${webbpm.security.token.issuer}")
private final String tokenIssuerName =
ResourceMetadataUtils.PROJECT_GROUP_ID + "." + ResourceMetadataUtils.PROJECT_ARTIFACT_ID;
private final SecretKey SIGNING_KEY;
@Autowired
public JwtTokenService(@Value("${webbpm.security.token.secret.key:ZjE5ZjMxNmYtODViZC00ZTQ5LWIxZmYtOGEzYzE3Yjc1MDVk}")
String secretKey) {
byte[] encodedKey = Base64.getDecoder().decode(secretKey);
this.SIGNING_KEY = Keys.hmacShaKeyFor(encodedKey);
}
public Token createAccessToken(String userAccountId, Long expiresIn, String ervuId) {
Date expirationDate = new Date(System.currentTimeMillis() + 1000L * expiresIn);
String value = Jwts.builder()
.setSubject(userAccountId + ":" + ervuId)
.setIssuer(tokenIssuerName)
.setIssuedAt(new Date(System.currentTimeMillis()))
.setExpiration(expirationDate)
.signWith(SIGNING_KEY)
.compact();
return new Token(userAccountId + ":" + ervuId, tokenIssuerName, expirationDate, value);
}
public boolean isValid(Token token) {
if (!tokenIssuerName.equals(token.getIssuer())) {
LOGGER.warn("Unknown token issuer {}", token.getIssuer());
return false;
}
if (token.isExpired()) {
LOGGER.info("Token {} is expired ", token.getValue());
return false;
}
return true;
}
public Token getToken(String token) {
Claims claims = Jwts.parser()
.setSigningKey(SIGNING_KEY)
.parseClaimsJws(token)
.getBody();
return new Token(claims.getSubject(), claims.getIssuer(), claims.getExpiration(), token);
}
}

View file

@ -1,25 +0,0 @@
package ru.micord.security;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.Customizer;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.web.SecurityFilterChain;
@Configuration
@EnableWebSecurity
//@EnableAuthorizationServer
public class SecurityConfig {
@Bean
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
http.csrf().disable()
.authorizeHttpRequests()
.antMatchers("/**")
.permitAll();
return http.build();
}
}

View file

@ -0,0 +1,10 @@
<jboss-deployment-structure>
<deployment>
<dependencies>
<module name="ru.CryptoPro.JCSP"/>
<module name="ru.CryptoPro.JCP.ASN"/>
<module name="ru.CryptoPro.JCP"/>
<module name="com.objsys.asn1j.runtime"/>
</dependencies>
</deployment>
</jboss-deployment-structure>

23
config/micord.env Normal file
View file

@ -0,0 +1,23 @@
TZ=Europe/Moscow
# App datasource
DB_APP_USERNAME=ervu-lkrp-fl
DB_APP_PASSWORD=ervu-lkrp-fl
DB_APP_HOST=10.10.31.119
DB_APP_PORT=5432
DB_APP_NAME=ervu-lkrp-fl
ESIA_SCOPES=snils, fullname, birthdate, id_doc
ESIA_BASE_URI=https://esia-portal1.test.gosuslugi.ru/
ESIA_CLIENT_ID=MNSV89
ESIA_REDIRECT_URL=https://lkrp-dev.micord.ru/fl/
SIGN_URL=https://ervu-sign-dev.k8s.micord.ru/sign
CLIENT_CERT_HASH=04508B4B0B58776A954A0E15F574B4E58799D74C61EE020B3330716C203E3BDD
ERVU_KAFKA_BOOTSTRAP_SERVERS=localhost:9092
ERVU_KAFKA_REPLY_TOPIC=ervu.lkpr.person.search.response
ERVU_KAFKA_GROUP_ID=1
ERVU_KAFKA_REQUEST_TOPIC=ervu.lkpr.person.search.request
ERVU_KAFKA_REPLY_TIMEOUT=30
ERVU_KAFKA_SEND_SECURITY_PROTOCOL=SASL_PLAINTEXT
ERVU_KAFKA_SASL_MECHANISM=SCRAM-SHA-256
ERVU_KAFKA_SEND_USERNAME=user1
ERVU_KAFKA_SEND_PASSWORD=Blfi9d2OFG

View file

@ -28,6 +28,17 @@ xa-data-source add \
/system-property=security.password.regex:add(value="^((?=(.*\\d){1,})(?=.*[a-zа-яё])(?=.*[A-ZА-ЯЁ]).{8,})$")
/system-property=fias.enable:add(value=false)
/system-property=bpmn.enable:add(value=false)
/system-property=esia.scopes:add(value="snils, fullname, birthdate, id_doc")
/system-property=esia.base.uri:add(value="https://esia-portal1.test.gosuslugi.ru/")
/system-property=esia.client.id:add(value="MNSV89")
/system-property=esia.redirect.url:add(value="https://lkrp-dev.micord.ru/fl/")
/system-property=sign.url:add(value="https://ervu-sign-dev.k8s.micord.ru/sign")
/system-property=client.cert.hash:add(value="04508B4B0B58776A954A0E15F574B4E58799D74C61EE020B3330716C203E3BDD")
/system-property=ervu.kafka.bootstrap.servers:add(value="localhost:9092")
/system-property=ervu.kafka.reply.topic:add(value="ervu.lkpr.person.search.response")
/system-property=ervu.kafka.group.id:add(value="1")
/system-property=ervu.kafka.request.topic:add(value="ervu.lkpr.person.search.request")
/system-property=ervu.kafka.reply.timeout:add(value="30")
/system-property=kafka.ervu.send.url:add(value="http://10.10.31.11:32609")
/system-property=kafka.ervu.security.protocol:add(value="SASL_PLAINTEXT")
/system-property=kafka.ervu.doc.login.module:add(value="org.apache.kafka.common.security.scram.ScramLoginModule")

View file

@ -54,6 +54,18 @@
<property name="security.password.regex" value="^((?=(.*\d){1,})(?=.*[a-zа-яё])(?=.*[A-ZА-ЯЁ]).{8,})$"/>
<property name="fias.enable" value="false"/>
<property name="com.arjuna.ats.arjuna.allowMultipleLastResources" value="true"/>
<property name="esia.scopes" value="snils, fullname, birthdate, id_doc"/>
<property name="esia.base.uri" value="https://esia-portal1.test.gosuslugi.ru/"/>
<property name="esia.client.id" value="MNSV89"/>
<property name="esia.redirect.url" value="https://lkrp.micord.ru"/>
<property name="sign.url" value="https://ervu-sign-dev.k8s.micord.ru/sign"/>
<property name="client.cert.hash" value="04508B4B0B58776A954A0E15F574B4E58799D74C61EE020B3330716C203E3BDD"/>
<property name="bpmn.enable" value="false"/>
<property name="ervu.kafka.bootstrap.servers" value="localhost:9092"/>
<property name="ervu.kafka.reply.topic" value="ervu.lkpr.person.search.response"/>
<property name="ervu.kafka.group.id" value="1"/>
<property name="ervu.kafka.request.topic" value="ervu.lkpr.person.search.request"/>
<property name="ervu.kafka.reply.timeout" value="30"/>
<property name="bpmn.enable" value="false"/>
<property name="kafka.ervu.send.url" value="http://10.10.31.11:32609"/>
<property name="kafka.ervu.security.protocol" value="SASL_PLAINTEXT"/>

View file

@ -0,0 +1,9 @@
#!/usr/bin/env bash
export JAVA_OPTS="$JAVA_OPTS \
-Ddb.app.host=${DB_APP_HOST:-db} \
-Ddb.app.port=${DB_APP_PORT:-5432} \
-Ddb.app.name=${DB_APP_NAME:-app} \
-Ddb.app.username=${DB_APP_USERNAME:-app_user} \
-Ddb.app.password=${DB_APP_PASSWORD:-apppassword} \
"

View file

@ -0,0 +1,36 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- The contents of this file will be loaded for each web application -->
<Context>
<!-- Default set of monitored resources. If one of these changes, the -->
<!-- web application will be reloaded. -->
<WatchedResource>WEB-INF/web.xml</WatchedResource>
<WatchedResource>WEB-INF/tomcat-web.xml</WatchedResource>
<WatchedResource>${catalina.base}/conf/web.xml</WatchedResource>
<!-- Uncomment this to disable session persistence across Tomcat restarts -->
<!--
<Manager pathname="" />
-->
<Resource name="java:/webbpm/AppDS" auth="Container"
type="javax.sql.DataSource" driverClassName="org.postgresql.Driver"
url="jdbc:postgresql://${db.app.host}:${db.app.port}/${db.app.name}"
username="${db.app.username}" password="${db.app.password}" maxTotal="20" maxIdle="10" maxWaitMillis="-1"/>
</Context>

View file

@ -0,0 +1,39 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<tomcat-users xmlns="http://tomcat.apache.org/xml"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://tomcat.apache.org/xml tomcat-users.xsd"
version="1.0">
<!--
By default, no user is included in the "manager-gui" role required
to operate the "/manager/html" web application. If you wish to use this app,
you must define such a user - the username and password are arbitrary.
Built-in Tomcat manager roles:
- manager-gui - allows access to the HTML GUI and the status pages
- manager-script - allows access to the HTTP API and the status pages
- manager-jmx - allows access to the JMX proxy and the status pages
- manager-status - allows access to the status pages only
The users below are wrapped in a comment and are therefore ignored. If you
wish to configure one or more of these users for use with the manager web
application, do not forget to remove the <!.. ..> that surrounds them. You
will also need to set the passwords to something appropriate.
-->
<user username="admin" password="<must-be-changed>" roles="manager-gui"/>
</tomcat-users>

View file

@ -0,0 +1,28 @@
# WebBPM properties
authentication.method=form
bpmn.enable=false
fias.enable=false
gar.enable=false
reset_password.mail.template.path=mail/reset_password.html
security.password.regex=^(?=.*[a-zA-Z])(?=.*[0-9])[a-zA-Z0-9]+$
webbpm.mode=production
webbpm.jbpm.hibernate_statistics.enabled=false
webbpm.cache.hazelcast.hosts=127.0.0.1
webbpm.cache.hazelcast.outbound_port_definitions=5801-5820
esia-scopes=snils, fullname, birthdate, id_doc
esia-org-scope-url=http://esia.gosuslugi.ru/
esia-uri.base-uri=https://esia-portal1.test.gosuslugi.ru/
esia-client-id=MNSV89
esia-redirect-url=https://lkrp-dev.micord.ru/ul/
sign-url=https://ervu-sign-dev.k8s.micord.ru/sign
client-cert-hash=04508B4B0B58776A954A0E15F574B4E58799D74C61EE020B3330716C203E3BDD
ervu-kafka.bootstrap-servers=localhost:9092
ervu-kafka.reply-topic=ervu.lkpr.person.search.response
ervu-kafka.group-id=1
ervu-kafka.request-topic=ervu.lkpr.person.search.request
ervu-kafka.reply-timeout=30

View file

@ -0,0 +1,26 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
Licensed to the Apache Software Foundation (ASF) under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The ASF licenses this file to You under the Apache License, Version 2.0
(the "License"); you may not use this file except in compliance with
the License. You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<Context antiResourceLocking="false" privileged="true" >
<CookieProcessor className="org.apache.tomcat.util.http.Rfc6265CookieProcessor"
sameSiteCookies="strict" />
<!--
<Valve className="org.apache.catalina.valves.RemoteAddrValve"
allow="d+\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
-->
<Manager sessionAttributeValueClassNameFilter="java\.lang\.(?:Boolean|Integer|Long|Number|String)|org\.apache\.catalina\.filters\.CsrfPreventionFilter\$LruCache(?:\$1)?|java\.util\.(?:Linked)?HashMap"/>
</Context>

View file

@ -5,7 +5,7 @@
"filter_cleanup_check_period_minutes": 30,
"auth_method": "form",
"enable.version.in.url": "%enable.version.in.url%",
"backend.context": "fl",
"backend.context": "fl/fl",
"guard.confirm_exit": false,
"message_service_error_timeout": "",
"message_service_warning_timeout": "",

View file

@ -1 +1 @@
%project.version%
1.0.0-SNAPSHOT

View file

@ -87,7 +87,13 @@ body.webbpm.ervu_lkrp_fl {
color: var(--white);
font-family: 'Inter';
}
.webbpm.ervu_lkrp_fl .header .header-logo .logo {
position: relative;
display: flex;
align-items: center;
}
.webbpm.ervu_lkrp_fl .header .header-logo .logo a {
position: absolute;
width: 62px;
height: 40px;
background: url(../img/svg/mil-logo.svg) no-repeat 0 50%;
@ -166,6 +172,11 @@ body.webbpm.ervu_lkrp_fl {
}
.webbpm.ervu_lkrp_fl footer {
position: relative;
top: auto;
bottom: auto;
left: auto;
right: auto;
height: var(--h-footer);
border: 0;
background-color: var(--color-text-primary);
@ -173,10 +184,15 @@ body.webbpm.ervu_lkrp_fl {
.webbpm.ervu_lkrp_fl .container {
padding-top: var(--h-header);
bottom: var(--h-footer);
bottom: 0;
}
.webbpm.ervu_lkrp_fl .container-inside {
font-family: 'Inter';
height: 100%;
padding: 0;
overflow: auto;
}
.webbpm.ervu_lkrp_fl .container-inside > div {
padding: var(--indent-huge) var(--w-screen);
}
@ -308,7 +324,7 @@ body.webbpm.ervu_lkrp_fl {
.webbpm.ervu_lkrp_fl .loader {
font-size: 15px;
left: calc(50% - 50px);
top: calc(50% - 50px);
top: calc(50% - 50px);
width: 0.8em;
height: 0.8em;
border-radius: 50%;

View file

@ -0,0 +1,5 @@
<button class="user-info" ngbDropdownToggle *ngIf="getIsAuth()">{{getUserFullname()}}</button>
<div ngbDropdownMenu *ngIf="getIsAuth()">
<a routerLink="/mydata" class="data">Мои данные</a>
<button ngbDropdownItem class="exit" (click)="logout()">Выйти</button>
</div>

View file

@ -5,8 +5,7 @@
<div class="container">
<div class="container-inside" id="webbpm-angular-application-container">
<router-outlet></router-outlet>
<app-footer *ngIf="footerVisible"></app-footer>
</div>
</div>
<app-footer *ngIf="footerVisible">
</app-footer>
</div>

View file

@ -0,0 +1,7 @@
import {Behavior, NotNull} from "@webbpm/base-package";
export class PersonData extends Behavior{
@NotNull()
public personDataId: string;
}

View file

@ -0,0 +1,33 @@
import {AnalyticalScope, Behavior, Container, ControlWithValue} from "@webbpm/base-package";
import {HttpClient} from "@angular/common/http";
import {PersonData} from "./PersonData";
import {CookieService} from "ngx-cookie";
import {PersonDataModel} from "../generated/ru/micord/ervu/security/esia/model/PersonDataModel";
@AnalyticalScope(Container)
export class PersonDataRoot extends Behavior{
private container: Container;
initialize() {
super.initialize();
this.container = this.getScript(Container);
let personScripts: PersonData[] = this.container.getScriptsInThisAndChildren(PersonData);
let httpClient = this.injector.get(HttpClient);
let cookieService = this.injector.get(CookieService);
if (cookieService.get("is_auth")) {
httpClient.get<PersonDataModel>("esia/person")
.toPromise()
.then(personModel => {
if (personModel == null) {
return;
}
for (let person of personScripts) {
let control: ControlWithValue = person.getScriptInObject(person.getObjectId(),
'component.ControlWithValue');
control.setValue(personModel[person.personDataId]);
}
});
}
}
}

View file

@ -1,6 +1,7 @@
import {NgModule} from "@angular/core";
import {RouterModule, Routes} from "@angular/router";
import {AccessDeniedComponent} from "./component/access-denied.component";
import {AuthGuard} from "../security/guard/auth.guard";
import {ConfirmExitGuard} from "@webbpm/base-package";
const appRoutes: Routes = [
@ -13,17 +14,17 @@ const appRoutes: Routes = [
{
path: 'mydata',
loadChildren: 'generated-sources/page-mydata.module#PagemydataModule',
canActivate: [ConfirmExitGuard],
canActivate: [AuthGuard],
},
{
path: 'restriction',
loadChildren: 'generated-sources/page-restriction.module#PagerestrictionModule',
canActivate: [ConfirmExitGuard],
canActivate: [AuthGuard],
},
{
path: 'subpoena',
loadChildren: 'generated-sources/page-subpoena.module#PagesubpoenaModule',
canActivate: [ConfirmExitGuard],
canActivate: [AuthGuard],
},
];

View file

@ -20,6 +20,7 @@ import {InternationalPhoneNumberModule} from "ngx-international-phone-number";
import {AppProgressIndicationComponent} from "./component/app-progress-indication.component";
import {AppProgressIndicationService} from "./service/app-progress-indication.service";
import {TextWithDialogLinks} from "../../ervu/component/textwithdialoglinks/TextWithDialogLinks";
import {LogOutComponent} from "./component/logout.component";
import {LoadForm} from "../../ervu/component/container/LoadForm";
import {InMemoryStaticGrid} from "../../ervu/component/grid/InMemoryStaticGrid";
@ -28,6 +29,7 @@ export const DIRECTIVES = [
forwardRef(() => AppHeaderComponent),
forwardRef(() => AppFooterComponent),
forwardRef(() => ApplicationVersionComponent),
forwardRef(() => LogOutComponent),
forwardRef(() => AccessDeniedComponent),
forwardRef(() => AppProgressIndicationComponent),
forwardRef(() => TextWithDialogLinks),

View file

@ -0,0 +1,43 @@
import {ChangeDetectorRef, Component, OnInit} from "@angular/core";
import {HttpClient} from "@angular/common/http";
import {CookieService} from "ngx-cookie";
@Component({
moduleId: module.id,
selector: "[log-out]",
templateUrl: "../../../../../src/resources/template/app/component/log_out.html"
})
export class LogOutComponent implements OnInit{
private userFullname: string;
constructor(private httpClient: HttpClient,
private cookieService: CookieService, private cd: ChangeDetectorRef) {
}
ngOnInit(): void {
let isAuth = this.getIsAuth();
if (isAuth) {
Promise.all([
this.httpClient.get<string>("esia/userfullname").toPromise(),
]).then(([userFullname]) => {
this.userFullname = userFullname;
this.cd.markForCheck();
});
}
}
public logout(): void {
this.httpClient.get<string>("esia/logout").toPromise().then(url => {
window.open(url, "_self");
})
}
public getUserFullname(): string {
return this.userFullname;
}
public getIsAuth(): boolean {
return this.cookieService.get("is_auth") != null;
}
}

View file

@ -0,0 +1,61 @@
import {Injectable} from "@angular/core";
import {ActivatedRouteSnapshot, CanActivate, Router, RouterStateSnapshot} from "@angular/router";
import {Observable} from "rxjs";
import {HttpClient, HttpParams} from "@angular/common/http";
import {CookieService} from "ngx-cookie";
@Injectable({providedIn:'root'})
export abstract class AuthGuard implements CanActivate {
protected constructor(
protected router: Router,
private httpClient: HttpClient,
private cookieService: CookieService
) {
}
public canActivate(route: ActivatedRouteSnapshot,
state: RouterStateSnapshot): Observable<boolean> | Promise<boolean> | boolean {
let hasAccess: Promise<boolean> | boolean = this.checkAccess();
return Promise.resolve(hasAccess).then((isAccess) => {
let url = new URL(window.location.href);
let params = new URLSearchParams(url.search);
let code = params.get('code');
let error = params.get('error');
let errorDescription = params.get('error_description');
if (isAccess) {
return true;
}
else if (error) {
throw new Error(error + ', error description =' + errorDescription);
}
else if (code) {
const params = new HttpParams().set('code', code);
this.httpClient.get<boolean>("esia/auth", {params: params}).toPromise().then(
() => window.open(url.origin + url.pathname, "_self"))
.catch((reason) =>
console.error(reason)
);
return false;
}
else {
this.httpClient.get<string>("esia/url")
.toPromise()
.then(url => window.open(url, "_self"));
return true;
}
}).catch((reason) => {
console.error(reason);
return false
});
}
private checkAccess(): Promise<boolean> | boolean {
return this.getIsAuth() != null;
};
public getIsAuth(): string {
return this.cookieService.get('is_auth');
}
}

View file

@ -1,14 +1,12 @@
import {NgModule} from "@angular/core";
import {RouterModule, Routes} from "@angular/router";
import {
ConfirmExitGuard
} from "@webbpm/base-package";
import {AuthGuard} from "../security/guard/auth.guard";
const webbpmRoutes: Routes = [
{
path: '',
loadChildren: 'generated-sources/page-lkfl.module#PagelkflModule',
canActivate: [ConfirmExitGuard],
canActivate: [AuthGuard],
pathMatch: 'full',
},
{

View file

@ -873,6 +873,751 @@
<enabled>false</enabled>
</scripts>
</children>
<removed>true</removed>
</children>
<children id="7245d5f5-da07-41ad-b56c-3d098c6bca75">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>7245d5f5-da07-41ad-b56c-3d098c6bca75</componentRootId>
<name>HB - main</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="d1732359-9b68-4f7c-9e81-b1e1bbf31349" removed="false">
<value>
<simple>"main-block"</simple>
</value>
</item>
</value>
</entry>
</properties>
</scripts>
<scripts id="b6068710-0f31-48ec-8e03-c0c1480a40c0"/>
<scripts id="fe04d7fb-6c5b-46c4-b723-667732d81f4f"/>
<scripts id="5c566210-2a60-4048-a2d1-84c7dd023248"/>
<scripts id="3171b2e1-b4af-4335-95fa-1b2592604b84"/>
<children id="3ed7cd92-3c7a-4d6f-a22c-1f3c4031bb61">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>3ed7cd92-3c7a-4d6f-a22c-1f3c4031bb61</componentRootId>
<name>VB - левый</name>
<container>true</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="59e8ca28-d5a7-4964-9b8f-ae9e28d50d31" removed="false">
<value>
<simple>"left-block"</simple>
</value>
</item>
</value>
</entry>
</properties>
</scripts>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<scripts id="df22d47b-adc3-47a6-9792-72462eb6b8ad">
<classRef type="TS">
<className>PersonDataRoot</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
</scripts>
<children id="5e98c4eb-ec87-453d-9fcb-666ae05ed1db">
<prototypeId>f7504fc9-f501-43fe-a678-5c6ba756ba5c</prototypeId>
<componentRootId>5e98c4eb-ec87-453d-9fcb-666ae05ed1db</componentRootId>
<name>FS</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="46f20297-81d1-4786-bb17-2a78ca6fda6f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="8efe7df2-4d95-434d-9b4a-237cc1a0f74d" removed="false">
<value>
<simple>"data-group"</simple>
</value>
</item>
</value>
</entry>
<entry>
<key>style</key>
<value>
<complex>
<entry>
<key>width</key>
<value>
<simple>null</simple>
</value>
</entry>
</complex>
</value>
</entry>
</properties>
</scripts>
<scripts id="7fe2f82f-5028-401e-941f-e92df36538a6"/>
<scripts id="73f52c22-5182-4860-8ee6-b9ba164ed460"/>
<scripts id="2129eba5-aac3-41d1-ba50-0a2f4b5f0a32"/>
<scripts id="865a51e1-80f5-4064-a7d2-2b251b33bdec"/>
<children id="9712b7a5-eb4c-4cab-a8dc-2c34e9b0d3f7">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>9712b7a5-eb4c-4cab-a8dc-2c34e9b0d3f7</componentRootId>
<name>VB</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f"/>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<children id="ab77b5e7-503a-4bb9-ad3e-a6bec053a0b0">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>ab77b5e7-503a-4bb9-ad3e-a6bec053a0b0</componentRootId>
<name>VB 1</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="1a1a5e58-950f-42e8-97ea-575a0394187c" removed="false">
<value>
<simple>"paragraph-group"</simple>
</value>
</item>
</value>
</entry>
<entry>
<key>style</key>
<value>
<complex>
<entry>
<key>height</key>
<value>
<simple>null</simple>
</value>
</entry>
</complex>
</value>
</entry>
</properties>
</scripts>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<children id="63e86970-41ec-41bb-8412-9ec28b8f1235">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>63e86970-41ec-41bb-8412-9ec28b8f1235</componentRootId>
<name>HB</name>
<container>true</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="9260bbbf-0ab1-4262-ba83-23974570b70c" removed="true"/>
<item id="ed63746b-ac10-441a-8a54-7a5755ec1a9f" removed="true"/>
</value>
</entry>
</properties>
</scripts>
<scripts id="b6068710-0f31-48ec-8e03-c0c1480a40c0"/>
<scripts id="fe04d7fb-6c5b-46c4-b723-667732d81f4f"/>
<scripts id="5c566210-2a60-4048-a2d1-84c7dd023248"/>
<scripts id="3171b2e1-b4af-4335-95fa-1b2592604b84"/>
<children id="f37ae541-813b-4b96-8cfa-8fb9b15feae5">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>f37ae541-813b-4b96-8cfa-8fb9b15feae5</componentRootId>
<name>Дата рождения</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="50a35647-07ed-4937-b4d3-4221a93060eb" removed="true"/>
</value>
</entry>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Дата рождения"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="96f09588-ac1f-487b-a0c9-ecb5c5db1000">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"birthDate"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="49bf8152-a4fd-4eb1-b457-0ad95f7a6e96">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>49bf8152-a4fd-4eb1-b457-0ad95f7a6e96</componentRootId>
<name>Снилс</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="76241bc1-5012-4e34-923d-9b6985ac0e86">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>76241bc1-5012-4e34-923d-9b6985ac0e86</componentRootId>
<name>Снилс</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Снилс"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="6c5d5c87-6106-4c29-a2cb-25dd331341ff">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"snils"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="872cf465-f5cb-48c0-8924-5df5ee899dda">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>872cf465-f5cb-48c0-8924-5df5ee899dda</componentRootId>
<name>VB</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="90b24715-744e-43a2-803f-3f46843741bb">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>90b24715-744e-43a2-803f-3f46843741bb</componentRootId>
<name>VB</name>
<container>true</container>
<removed>true</removed>
</children>
</children>
</children>
<children id="63e86970-41ec-41bb-8412-9ec28b8f1235">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>63e86970-41ec-41bb-8412-9ec28b8f1235</componentRootId>
<name>HB</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="126b07a0-52bf-44aa-a5e2-c14eebedea87">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>126b07a0-52bf-44aa-a5e2-c14eebedea87</componentRootId>
<name>Паспорт</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="91bc304c-8b1e-4ad7-be05-dfc9b8069a62">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>91bc304c-8b1e-4ad7-be05-dfc9b8069a62</componentRootId>
<name>Паспорт 1</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="96e87283-d6c8-44c8-89b6-922e528e3279">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>96e87283-d6c8-44c8-89b6-922e528e3279</componentRootId>
<name>Серия и номер</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="bc7fc5b5-efe5-4675-9726-c207dab21f58">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>bc7fc5b5-efe5-4675-9726-c207dab21f58</componentRootId>
<name>Выдан</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="27832ab8-cf86-4cd7-b179-0b4933ddb1e2">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>27832ab8-cf86-4cd7-b179-0b4933ddb1e2</componentRootId>
<name>HB</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="c8cfd2f3-22e3-4518-8770-ac148c7f7f00">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>c8cfd2f3-22e3-4518-8770-ac148c7f7f00</componentRootId>
<name>VB 2</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="13ca0551-0937-4e95-a23d-4bf7e0967b10" removed="false">
<value>
<simple>"paragraph-group"</simple>
</value>
</item>
</value>
</entry>
</properties>
</scripts>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<children id="126b07a0-52bf-44aa-a5e2-c14eebedea87">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>126b07a0-52bf-44aa-a5e2-c14eebedea87</componentRootId>
<name>Паспорт</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="ddf92f21-aac9-4378-b2e7-3884fa0b1164" removed="false">
<value>
<simple>"font-bold"</simple>
</value>
</item>
</value>
</entry>
<entry>
<key>initialValue</key>
<value>
<simple>"Паспорт"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
</children>
<children id="e4fde7fa-cb62-4d83-953c-4704a9d549c5">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>e4fde7fa-cb62-4d83-953c-4704a9d549c5</componentRootId>
<name>Серия и номер</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Серия и номер"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="97063d8a-228c-410e-8365-081e2834b5bb">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"seriesAndNumber"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="de1f60b2-f0c6-4688-97d1-6ee11277d088">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>de1f60b2-f0c6-4688-97d1-6ee11277d088</componentRootId>
<name>Выдан</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Выдан"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="779ec208-5592-4e30-af59-473e4ea92563">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"issuedBy"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="96e87283-d6c8-44c8-89b6-922e528e3279">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>96e87283-d6c8-44c8-89b6-922e528e3279</componentRootId>
<name>Серия и номер</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="bc7fc5b5-efe5-4675-9726-c207dab21f58">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>bc7fc5b5-efe5-4675-9726-c207dab21f58</componentRootId>
<name>Выдан</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="27832ab8-cf86-4cd7-b179-0b4933ddb1e2">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>27832ab8-cf86-4cd7-b179-0b4933ddb1e2</componentRootId>
<name>HB</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f"/>
<scripts id="b6068710-0f31-48ec-8e03-c0c1480a40c0"/>
<scripts id="fe04d7fb-6c5b-46c4-b723-667732d81f4f"/>
<scripts id="5c566210-2a60-4048-a2d1-84c7dd023248"/>
<scripts id="3171b2e1-b4af-4335-95fa-1b2592604b84"/>
<children id="17ca8fc6-713f-4366-b76b-abc7aff691cf">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>17ca8fc6-713f-4366-b76b-abc7aff691cf</componentRootId>
<name>Дата выдачи</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Дата выдачи"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="0ba1b7fe-4af3-4575-860a-c37bc30338ce">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"issueDate"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="b94fc4cc-1b8e-47c2-a26d-d1b11338960f">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>b94fc4cc-1b8e-47c2-a26d-d1b11338960f</componentRootId>
<name>Дата выдачи</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="dee2df94-288c-4f4f-8823-04cc24053851">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>dee2df94-288c-4f4f-8823-04cc24053851</componentRootId>
<name>VB</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="03d0f690-8fd8-4c1f-8a34-ae33d837a51d">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>03d0f690-8fd8-4c1f-8a34-ae33d837a51d</componentRootId>
<name>VB</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="48188ed6-8779-4ecc-920c-a7253e41c8b3">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>48188ed6-8779-4ecc-920c-a7253e41c8b3</componentRootId>
<name>Код подразделения</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="c8043649-bab5-4f5b-a4e1-0538629c3735">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>c8043649-bab5-4f5b-a4e1-0538629c3735</componentRootId>
<name>Код подразделения</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
<entry>
<key>label</key>
<value>
<simple>"Код подразделения"</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="709fa9c9-f418-45bc-86d7-edcaca0b5740">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"issueId"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
</children>
</children>
</children>
</children>
</children>
<children id="5e98c4eb-ec87-453d-9fcb-666ae05ed1db">
<prototypeId>f7504fc9-f501-43fe-a678-5c6ba756ba5c</prototypeId>
<componentRootId>5e98c4eb-ec87-453d-9fcb-666ae05ed1db</componentRootId>
<name>FS</name>
<container>true</container>
<removed>true</removed>
</children>
<children id="4c4dd675-4420-48ac-b0de-d1af4a9c01fd">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>4c4dd675-4420-48ac-b0de-d1af4a9c01fd</componentRootId>
<name>VB - правый</name>
<container>true</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="254b397c-33f2-46f7-adba-03fea5332a2b" removed="false">
<value>
<simple>"right-block"</simple>
</value>
</item>
</value>
</entry>
</properties>
</scripts>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<children id="e173df16-9759-4708-b9da-041722b87810">
<prototypeId>f7504fc9-f501-43fe-a678-5c6ba756ba5c</prototypeId>
<componentRootId>e173df16-9759-4708-b9da-041722b87810</componentRootId>
<name>FS - (количество дней до явки в военкомат)</name>
<container>true</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="46f20297-81d1-4786-bb17-2a78ca6fda6f">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="d36f40dc-c5c2-41de-a4e7-2ce5beb98e83" removed="false">
<value>
<simple>"data-group"</simple>
</value>
</item>
</value>
</entry>
</properties>
</scripts>
<scripts id="7fe2f82f-5028-401e-941f-e92df36538a6"/>
<scripts id="73f52c22-5182-4860-8ee6-b9ba164ed460"/>
<scripts id="2129eba5-aac3-41d1-ba50-0a2f4b5f0a32"/>
<scripts id="865a51e1-80f5-4064-a7d2-2b251b33bdec"/>
<children id="526d971b-c75a-4ac6-a195-d70b73d58508">
<prototypeId>9d1b5af1-0b8f-4b1b-b9a5-c2e6acf72d91</prototypeId>
<componentRootId>526d971b-c75a-4ac6-a195-d70b73d58508</componentRootId>
<name>VB</name>
<container>true</container>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f"/>
<scripts id="72befe90-1915-483f-b88c-d1ec5d4bdc8e"/>
<scripts id="87f3fefa-b77b-4137-aab6-b2bcd83ce380"/>
<scripts id="ef21ca22-3f81-4484-ba6f-58d670c12d4f"/>
<scripts id="277e6fbc-9e2e-4080-bf20-5d8be18e6764"/>
<children id="b0e158fe-6b76-4104-af7f-9526d86f4c8b">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>b0e158fe-6b76-4104-af7f-9526d86f4c8b</componentRootId>
<name>Данные получены с портала Госуслуг</name>
<container>false</container>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>initialValue</key>
<value>
<simple>"Данные получены с портала Госуслуг"</simple>
</value>
</entry>
<entry>
<key>style</key>
<value>
<complex>
<entry>
<key>width</key>
<value>
<simple>null</simple>
</value>
</entry>
</complex>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
</children>
<children id="5b36ac8e-2682-4ec8-9e48-57e7412c8fd2">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>
<componentRootId>5b36ac8e-2682-4ec8-9e48-57e7412c8fd2</componentRootId>
<name>Данные получены с портала Госуслуг</name>
<container>false</container>
<removed>true</removed>
</children>
<children id="f8ee739c-7e9e-4880-866c-b5dd1161c297">
<prototypeId>d7d54cfb-26b5-4dba-b56f-b6247183c24d</prototypeId>
<componentRootId>f8ee739c-7e9e-4880-866c-b5dd1161c297</componentRootId>
<name>HB - дата. Если заметили</name>
<container>true</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="bf098f19-480e-44e4-9084-aa42955c4d0f"/>
<scripts id="b6068710-0f31-48ec-8e03-c0c1480a40c0"/>
<scripts id="fe04d7fb-6c5b-46c4-b723-667732d81f4f"/>
<scripts id="5c566210-2a60-4048-a2d1-84c7dd023248"/>
<scripts id="3171b2e1-b4af-4335-95fa-1b2592604b84"/>
<children id="6812c23a-c407-450c-9312-a76a81a3c069">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>6812c23a-c407-450c-9312-a76a81a3c069</componentRootId>

View file

@ -147,6 +147,63 @@
<name>ФИО</name>
<container>false</container>
<removed>true</removed>
<scripts id="a4cf549b-0153-4439-a2c2-8f32101ed102">
<classRef type="TS">
<className>PersonDataRoot</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
</scripts>
<children id="fe895e77-d4f6-4cdb-b6f1-02b4b4a0e429">
<prototypeId>ba24d307-0b91-4299-ba82-9d0b52384ff2</prototypeId>
<componentRootId>fe895e77-d4f6-4cdb-b6f1-02b4b4a0e429</componentRootId>
<name>ФИО</name>
<container>false</container>
<expanded>false</expanded>
<childrenReordered>false</childrenReordered>
<scripts id="cf4526a1-96ab-4820-8aa9-62fb54c2b64c">
<properties>
<entry>
<key>cssClasses</key>
<value>
<item id="3d27dc24-ebaf-441f-bbfc-493e001a6731" removed="false">
<value>
<simple>"title"</simple>
</value>
</item>
</value>
</entry>
<entry>
<key>initialValue</key>
<value>
<simple>null</simple>
</value>
</entry>
</properties>
</scripts>
<scripts id="737b67e2-295f-4356-a1e1-9419344d8c85"/>
<scripts id="a6ccccd9-354c-4725-9d34-c716cf626048"/>
<scripts id="d38c1af5-2bfe-41cd-ab0f-67040f498127"/>
<scripts id="f203f156-be32-4131-9c86-4d6bac6d5d56">
<enabled>false</enabled>
</scripts>
<scripts id="82788e01-59b4-430a-943a-63487e011f00">
<classRef type="TS">
<className>PersonData</className>
<packageName>esia</packageName>
</classRef>
<enabled>true</enabled>
<expanded>true</expanded>
<properties>
<entry>
<key>personDataId</key>
<value>
<simple>"fullname"</simple>
</value>
</entry>
</properties>
</scripts>
</children>
<children id="367d1b29-5968-49be-9d34-a30ed45fdb57">
<prototypeId>133ca212-09a6-413a-ac66-e2f6ce188f1f</prototypeId>

View file

@ -1,27 +0,0 @@
import old.*;
import org.junit.platform.suite.api.SelectClasses;
import org.junit.platform.suite.api.Suite;
import tests.AuthoritiesIT;
import tests.LoginIT;
import tests.OrganizationsIT;
import tests.ProcessesIT;
/**
* @author gulnaz
*/
@Suite
@SelectClasses({
AuthoritiesIT.class,
LoginIT.class,
OrganizationsIT.class,
ProcessesIT.class,
AdminGroupIT.class,
AdminRoleIT.class,
AdminUserIT.class,
JWTokensIT.class
})
public class SuiteAdmin {
SuiteAdmin() {
}
}

View file

@ -1,332 +0,0 @@
package old;
import com.google.common.collect.Comparators;
import old.core.Browser;
import old.core.BrowserArgumentProvider;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.api.TestInfo;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import old.page.AdminGroupPage;
import old.page.AdminUserPage;
import java.util.Arrays;
import java.util.List;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNotEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
/**
* @author kote
*/
public class AdminGroupIT extends BaseComponentIT {
private static final String GROUP_ACCESS_LEVEL = "user access level";
private static final String ROLE = "BPMN User";
private static final String ROLE_2 = "BPMN Admin";
private static final String ROLE_3 = "BPMN Superuser";
private static final String COL_ID = "group$name";
private static final String COL_ID_CREATED = "group$created";
private static final String COL_ID_UPDATED = "group$updated";
private static final String BPMN_ADMIN_ROLE_ID = "aa14ba1d-0b61-4e33-8474-7c2d98944b12";
private static final String BPMN_USER_ROLE_ID = "767ae8cf-af01-44d4-86ef-fcb143373407";
private static final String BPMN_SUPERUSER_ROLE_ID = "2569ba58-1f8f-43ea-8b2c-0d373cf501fe";
private AdminGroupPage adminGroupPage;
private String oldName;
private String groupId;
private String roleId;
public AdminGroupIT() {
super();
}
@AfterEach
public void afterEachTest(TestInfo testInfo) {
String testName = testInfo.getTestMethod().toString();
if (testName.contains("User")) {
EXECUTION_MANAGER.deleteTestUser(name);
}
if (testName.contains("edit")) {
EXECUTION_MANAGER.deleteTestGroup(oldName);
}
if (testName.contains("linked")) {
EXECUTION_MANAGER.deleteUserGroupRole(name, groupId, roleId);
}
if (testName.contains("Sorting")) {
String groupIdToDelete = EXECUTION_MANAGER.getGroupIdByName(name);
EXECUTION_MANAGER.deleteLinkedRolesFromGroup(groupIdToDelete);
}
EXECUTION_MANAGER.deleteTestGroup(name);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void createGroup(Browser browser) {
openBrowserAndAdminPage(browser);
adminGroupPage.clickCreateButton();
adminGroupPage.waitForPageLoad();
adminGroupPage.waitForVisibilityOf(adminGroupPage.nameField);
adminGroupPage.typeText(adminGroupPage.nameField, name);
adminGroupPage.typeAndSelectLevel(GROUP_ACCESS_LEVEL);
adminGroupPage.addRole(ROLE, false);
adminGroupPage.clickSaveButton();
String dateOfCreation = adminGroupPage.getLocalDate();
adminGroupPage.waitForPageLoad();
adminGroupPage.searchGroup(name);
assertEquals(1, adminGroupPage.getListOfGroupsNamesFromTable(name).size());
assertTrue(adminGroupPage.getActionTime(COL_ID, name, COL_ID_CREATED).getText().contains(dateOfCreation));
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void searchGroup(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestGroup(name, ACCESS_LEVEL_ID);
adminGroupPage.searchGroup(name);
adminGroupPage.waitForPageLoad();
assertEquals(1, adminGroupPage.getListOfGroupsNamesFromTable(name).size());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void editGroup(Browser browser) {
openBrowserAndAdminPage(browser);
oldName = "old" + name;
EXECUTION_MANAGER.createTestGroup(oldName, ACCESS_LEVEL_ID);
adminGroupPage.chooseGroup(oldName);
adminGroupPage.clickEditButton();
adminGroupPage.waitForVisibilityOf(adminGroupPage.nameField);
adminGroupPage.typeText(adminGroupPage.nameField, name);
adminGroupPage.addRole(ROLE, false);
adminGroupPage.clickSaveButton();
adminGroupPage.searchGroup(oldName);
assertEquals(0, adminGroupPage.getListOfGroupsNamesFromTable(oldName).size());
adminGroupPage.chooseGroup(name);
assertEquals(1, adminGroupPage.getListOfGroupsNamesFromTable(name).size());
String timeOfCreate = adminGroupPage.getActionTime(COL_ID, name, COL_ID_CREATED).getText();
String timeOfUpdate = adminGroupPage.getActionTime(COL_ID, name, COL_ID_UPDATED).getText();
assertNotEquals(timeOfCreate, timeOfUpdate);
adminGroupPage.clickEditButton();
assertTrue(adminGroupPage.hasRolesInTable(AdminGroupPage.GroupPageGrids.ADDED_ROLES_GRID, ROLE));
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void deleteGroup(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestGroup(name, ACCESS_LEVEL_ID);
adminGroupPage.chooseGroup(name);
adminGroupPage.deleteGroup();
assertTrue(adminGroupPage.isGridEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void linkedRolesTable(Browser browser) {
openBrowserAndAdminPage(browser);
roleId = EXECUTION_MANAGER.generateId();
groupId = EXECUTION_MANAGER.generateId();
EXECUTION_MANAGER.createBindGroupRole(name, groupId, ACCESS_LEVEL_ID, roleId);
adminGroupPage.chooseGroup(name);
assertEquals(1, adminGroupPage.getListOfRolesFromLinkedTable().size());
assertEquals(name, adminGroupPage.getListOfRolesFromLinkedTable().get(0).getText());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void attachRemoveRoleToGroup(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestGroup(name, ACCESS_LEVEL_ID);
adminGroupPage.chooseGroup(name);
assertTrue(adminGroupPage.getListOfRolesFromLinkedTable().isEmpty());
adminGroupPage.clickEditButton();
assertFalse(adminGroupPage.getListOfRolesToAdd().isEmpty());
assertTrue(adminGroupPage.getListOfAddedRoles().isEmpty());
adminGroupPage.addRole(ROLE, false);
assertFalse(adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd()).contains(ROLE));
assertTrue(adminGroupPage.getWebElementTexts(adminGroupPage.getListOfAddedRoles()).contains(ROLE));
assertEquals(1, adminGroupPage.getListOfAddedRoles().size());
adminGroupPage.clickSaveButton();
adminGroupPage.chooseGroup(name);
assertEquals(1, adminGroupPage.getListOfRolesFromLinkedTable().size());
assertTrue(adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesFromLinkedTable()).contains(ROLE));
adminGroupPage.clickEditButton();
adminGroupPage.removeRole(ROLE);
assertTrue(adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd()).contains(ROLE));
assertTrue(adminGroupPage.getListOfAddedRoles().isEmpty());
adminGroupPage.clickSaveButton();
adminGroupPage.chooseGroup(name);
assertTrue(adminGroupPage.getListOfRolesFromLinkedTable().isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void attachRemoveAllRolesToGroup(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestGroup(name, ACCESS_LEVEL_ID);
List<String> roleNames = EXECUTION_MANAGER.getRoleNamesFromUserRole();
List<String> expectedRoles = Arrays.asList(ROLE, ROLE_2, ROLE_3);
adminGroupPage.chooseGroup(name);
adminGroupPage.clickEditButton();
assertFalse(adminGroupPage.getListOfRolesToAdd().isEmpty());
assertTrue(adminGroupPage.getListOfAddedRoles().isEmpty());
adminGroupPage.addAllRoles();
assertTrue(adminGroupPage.isAvailableGridEmpty(roleNames));
assertFalse(adminGroupPage.getListOfAddedRoles().isEmpty());
/*
Нет возможности проверить сохранение привязки всех ролей к группе из-за создания/удаление ролей
параллельными тестами.
*/
adminGroupPage.removeAllRoles();
assertFalse(adminGroupPage.getListOfRolesToAdd().isEmpty());
assertTrue(adminGroupPage.getListOfAddedRoles().isEmpty());
adminGroupPage.addRole(ROLE, false);
adminGroupPage.addRole(ROLE_2, false);
adminGroupPage.addRole(ROLE_3, false);
adminGroupPage.clickSaveButton();
adminGroupPage.chooseGroup(name);
assertEquals(expectedRoles.size(), adminGroupPage.getListOfRolesFromLinkedTable().size());
assertTrue(adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesFromLinkedTable())
.containsAll(expectedRoles));
adminGroupPage.clickEditButton();
adminGroupPage.removeAllRoles();
adminGroupPage.clickSaveButton();
adminGroupPage.chooseGroup(name);
assertTrue(adminGroupPage.getListOfRolesFromLinkedTable().isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void addNewGroupToUser(Browser browser) {
openBrowserAndAdminPage(browser);
String userName = name;
EXECUTION_MANAGER.createUser(userName, ORGANIZATION_ID);
adminGroupPage.clickCreateButton();
adminGroupPage.waitForPageLoad();
adminGroupPage.waitForVisibilityOf(adminGroupPage.nameField);
adminGroupPage.typeText(adminGroupPage.nameField, name);
adminGroupPage.typeAndSelectLevel(GROUP_ACCESS_LEVEL);
adminGroupPage.clickSaveButton();
AdminUserPage adminUserPage = inboxPage.startAdminUser();
adminUserPage.searchUser(userName);
adminUserPage.clickOnUserInTable(userName);
adminUserPage.clickEditButton();
adminUserPage.fillPassAndEmail(userName, userName + "@test.ru");
adminUserPage.bindGroup(name);
assertTrue(adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups()).contains(name));
adminUserPage.clickSaveButton();
adminUserPage.searchUser(userName);
adminUserPage.clickOnUserInTable(userName);
assertEquals(1, adminUserPage.getListOfGroupsFromTable().size());
assertEquals(name, adminUserPage.getListOfGroupsFromTable().get(0).getText());
}
@Disabled("dev WEBBPMNEXT-7837")
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void groupRolesGridsSorting(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createGroupBindRoles(name, ACCESS_LEVEL_ID, BPMN_ADMIN_ROLE_ID,
BPMN_USER_ROLE_ID, BPMN_SUPERUSER_ROLE_ID);
//main group page sorting
List<String> groupNamesNatural = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfGroupNames());
assertTrue(Comparators.isInOrder(groupNamesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.GROUP_NAMES_GRID);
List<String> groupNamesReverse = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfGroupNames());
assertTrue(Comparators.isInOrder(groupNamesReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
adminGroupPage.chooseGroup(name);
List<String> linkedRolesNatural = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesFromLinkedTable());
assertTrue(Comparators.isInOrder(linkedRolesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.LINKED_ROLES_GRID);
List<String> linkedRolesReverse = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesFromLinkedTable());
assertTrue(Comparators.isInOrder(linkedRolesReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
//edit group page sorting
adminGroupPage.clickEditButton();
List<String> availableToAddRolesNatural = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd());
assertTrue(Comparators.isInOrder(availableToAddRolesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.ROLES_TO_ADD_GRID);
List<String> availableToAddRolesReverse = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd());
assertTrue(Comparators.isInOrder(availableToAddRolesReverse,
String.CASE_INSENSITIVE_ORDER.reversed()), "Grid wasn't sorted");
adminGroupPage.removeAllRoles();
List<String> addedRolesNatural = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfAddedRoles());
assertTrue(Comparators.isInOrder(addedRolesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.ADDED_ROLES_GRID);
List<String> addedRolesReverse = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfAddedRoles());
assertTrue(Comparators.isInOrder(addedRolesReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
//create group page sorting
adminGroupPage.cancelAction();
adminGroupPage.clickCreateButton();
List<String> rolesToAddNatural = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd());
assertTrue(Comparators.isInOrder(rolesToAddNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.ROLES_TO_ADD_GRID);
List<String> rolesToAddReverse = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfRolesToAdd());
assertTrue(Comparators.isInOrder(rolesToAddReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
adminGroupPage.removeAllRoles();
List<String> addedRolesNaturalSort = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfAddedRoles());
assertTrue(Comparators.isInOrder(addedRolesNaturalSort, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminGroupPage.changeGroupPageGridSort(AdminGroupPage.GroupPageGrids.ADDED_ROLES_GRID);
List<String> addedRolesReverseSort = adminGroupPage.getWebElementTexts(adminGroupPage.getListOfAddedRoles());
assertTrue(Comparators.isInOrder(addedRolesReverseSort, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
}
private void openBrowserAndAdminPage(Browser browser) {
openBrowserAndLoginForAdmin(browser);
initAdminName();
adminGroupPage = inboxPage.startAdminGroup();
}
}

View file

@ -1,184 +0,0 @@
package old;
import com.google.common.collect.Comparators;
import old.core.Browser;
import old.core.BrowserArgumentProvider;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.api.TestInfo;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import org.openqa.selenium.WebElement;
import old.page.AdminGroupPage;
import old.page.AdminRolePage;
import java.util.List;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
/**
* @author kote
*/
public class AdminRoleIT extends BaseComponentIT {
private static final String COL_ID = "role$name";
private static final String COL_ID_CREATED = "role$created";
private static final String COL_ID_UPDATED = "role$updated";
private AdminRolePage adminRolePage;
private String oldName;
public AdminRoleIT() {
super();
}
@AfterEach
public void afterEachTest(TestInfo testInfo) {
String testName = testInfo.getTestMethod().toString();
if (testName.contains("Group")) {
EXECUTION_MANAGER.deleteTestGroup(name);
}
if (testName.contains("edit")) {
EXECUTION_MANAGER.deleteTestRole(oldName);
}
if (testName.contains("Sorting")) {
String roleId = EXECUTION_MANAGER.getRoleIdByName(name);
EXECUTION_MANAGER.deleteLinkedGroupsFromRole(roleId);
}
EXECUTION_MANAGER.deleteTestRole(name);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void createRole(Browser browser) {
openBrowserAndAdminPage(browser);
adminRolePage.clickCreateButton();
adminRolePage.typeText(adminRolePage.nameField, name);
adminRolePage.clickSaveButton();
String dateOfCreation = adminRolePage.getLocalDate();
adminRolePage.searchRole(name);
assertEquals(1, adminRolePage.getListOfRolesNamesFromTable(name).size());
assertTrue(adminRolePage.getActionTime(COL_ID, name, COL_ID_CREATED).getText().contains(dateOfCreation));
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void searchRole(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestRole(name);
adminRolePage.searchRole(name);
assertEquals(1, adminRolePage.getListOfRolesNamesFromTable(name).size());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void editRole(Browser browser) {
openBrowserAndAdminPage(browser);
oldName = "old" + name;
EXECUTION_MANAGER.createTestRole(oldName);
adminRolePage.chooseRole(oldName);
adminRolePage.clickEditButton();
adminRolePage.typeText(adminRolePage.nameField, name);
adminRolePage.clickSaveButton();
adminRolePage.searchRole(oldName);
assertEquals(0, adminRolePage.getListOfRolesNamesFromTable(oldName).size());
adminRolePage.searchRole(name);
assertEquals(1, adminRolePage.getListOfRolesNamesFromTable(name).size());
String timeOfCreate = adminRolePage.getActionTime(COL_ID, name, COL_ID_CREATED).getText();
String timeOfUpdate = adminRolePage.getActionTime(COL_ID, name, COL_ID_UPDATED).getText();
assertNotEquals(timeOfCreate, timeOfUpdate);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void deleteRole(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestRole(name);
adminRolePage.waitForPageLoad();
adminRolePage.chooseRole(name);
adminRolePage.deleteRole();
assertEquals(0, adminRolePage.getListOfRolesNamesFromTable(name).size());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void roleGroupGridContainsAttachedGroup(Browser browser) {
openBrowserAndAdminPage(browser);
String roleId = EXECUTION_MANAGER.generateId();
String groupId = EXECUTION_MANAGER.generateId();
EXECUTION_MANAGER.createBindGroupRole(name, groupId, ACCESS_LEVEL_ID, roleId);
adminRolePage.chooseRole(name);
WebElement gridLinkedGroup = adminRolePage.getListOfRoleLinkedGroups().get(0);
adminRolePage.waitForTextToBePresentInElement(gridLinkedGroup, name);
assertEquals(1, adminRolePage.getListOfRoleLinkedGroups().size());
assertEquals(adminRolePage.getListOfRoleLinkedGroups().get(0).getText(), name);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void addNewRoleToGroup(Browser browser) {
openBrowserAndAdminPage(browser);
String groupName = name;
EXECUTION_MANAGER.createTestGroup(groupName, ACCESS_LEVEL_ID);
adminRolePage.clickCreateButton();
adminRolePage.typeText(adminRolePage.nameField, name);
adminRolePage.clickSaveButton();
AdminGroupPage adminGroupPage = inboxPage.startAdminGroup();
adminGroupPage.chooseGroup(groupName);
adminGroupPage.clickEditButton();
adminGroupPage.bindRole(name);
assertTrue(adminGroupPage.hasRolesInTable(AdminGroupPage.GroupPageGrids.ADDED_ROLES_GRID, name));
adminGroupPage.clickSaveButton();
adminGroupPage.chooseGroup(groupName);
adminGroupPage.clickEditButton();
assertTrue(adminGroupPage.hasRolesInTable(AdminGroupPage.GroupPageGrids.ADDED_ROLES_GRID, name));
}
@Disabled("dev WEBBPMNEXT-7837")
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void roleGroupsGridSorting(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createRoleBindGroups(name, BPMN_ADMIN_GROUP_ID, BPMN_USER_GROUP_ID, BPMN_SUPERUSER_GROUP_ID);
List<String> roleNamesNatural = adminRolePage.getWebElementTexts(adminRolePage.getListOfRoles());
assertTrue(Comparators.isInOrder(roleNamesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminRolePage.changeRolePageGridSort(AdminRolePage.RolePageGrids.ROLE_NAMES_GRID);
List<String> roleNamesReverse = adminRolePage.getWebElementTexts(adminRolePage.getListOfRoles());
assertTrue(Comparators.isInOrder(roleNamesReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
adminRolePage.chooseRole(name);
List<String> linkedGroupsNatural = adminRolePage.getWebElementTexts(adminRolePage.getListOfRoleLinkedGroups());
assertTrue(Comparators.isInOrder(linkedGroupsNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminRolePage.changeRolePageGridSort(AdminRolePage.RolePageGrids.GROUP_NAMES_GRID);
List<String> linkedGroupsReverse = adminRolePage.getWebElementTexts(adminRolePage.getListOfRoleLinkedGroups());
assertTrue(Comparators.isInOrder(linkedGroupsReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
}
private void openBrowserAndAdminPage(Browser browser) {
openBrowserAndLoginForAdmin(browser);
initAdminName();
adminRolePage = inboxPage.startAdminRole();
}
}

View file

@ -1,370 +0,0 @@
package old;
import com.google.common.collect.Comparators;
import old.core.Browser;
import old.core.BrowserArgumentProvider;
import org.apache.commons.lang.RandomStringUtils;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.api.TestInfo;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import old.page.AdminUserPage;
import java.util.Arrays;
import java.util.List;
import static org.apache.commons.lang.StringUtils.containsIgnoreCase;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNotEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
/**
* @author kote
*/
public class AdminUserIT extends BaseComponentIT {
private AdminUserPage adminUserPage;
private String oldName;
private String email;
private static final String USER_PASSWORD = "test";
private static final String USER_PASSWORD_2 = "test2";
private static final String ORGANIZATION = "Default";
private static final String FULL_ORGANIZATION_NAME = "Default Organization";
private static final String BPMN_ADMIN_GROUP = "BPMN Admin";
private static final String BPMN_USER_GROUP = "BPMN User";
private static final String BPMN_SUPERUSER_GROUP = "BPMN Superuser";
private static final String SECURITY_GROUP = "Security Admin";
public AdminUserIT() {
super();
}
@AfterEach
public void afterEachTest(TestInfo testInfo) {
String testName = testInfo.getTestMethod().toString();
if (testName.contains("edit")) {
EXECUTION_MANAGER.deleteTestUser(oldName);
}
if (containsIgnoreCase(testName, "sorting")) {
String userAccId = EXECUTION_MANAGER.getUserAccountIdByName(name);
EXECUTION_MANAGER.deleteUserLinkedGroups(userAccId);
}
if (containsIgnoreCase(testName, "visibility")) {
String userAccountId = EXECUTION_MANAGER.getUserAccountIdByName(name);
EXECUTION_MANAGER.deleteUserLinkedGroups(userAccountId);
}
EXECUTION_MANAGER.deleteTestUser(name);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void createUser(Browser browser) {
openBrowserAndAdminPage(browser);
adminUserPage.clickCreateButton();
adminUserPage.waitForVisibilityOf(adminUserPage.lastNameField);
adminUserPage.fillUserFullName(name);
email = randomEmail();
adminUserPage.fillUserCredentials(name, USER_PASSWORD, email, ORGANIZATION, FULL_ORGANIZATION_NAME);
adminUserPage.addGroup(BPMN_ADMIN_GROUP);
adminUserPage.clickSaveButton();
assertTrue(EXECUTION_MANAGER.hasUserByData(name, email));
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertEquals(1, adminUserPage.getListOfGroupsFromTable().size());
assertEquals(BPMN_ADMIN_GROUP, adminUserPage.getListOfGroupsFromTable().get(0).getText());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void searchUser(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
adminUserPage.searchUser(name);
assertEquals(1, adminUserPage.getListOfLastNamesFromTable().size());
assertEquals(1, adminUserPage.getListOfFirstNamesFromTable().size());
assertEquals(1, adminUserPage.getListOfMiddleNamesFromTable().size());
assertEquals(name, adminUserPage.getListOfLastNamesFromTable().get(0).getText());
assertEquals(name, adminUserPage.getListOfFirstNamesFromTable().get(0).getText());
assertEquals(name, adminUserPage.getListOfMiddleNamesFromTable().get(0).getText());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void editUser(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
adminUserPage.clickEditButton();
adminUserPage.waitForVisibilityOf(adminUserPage.lastNameField);
oldName = name;
name = name + "_edited";
adminUserPage.fillUserFullName(name);
email = randomEmail();
adminUserPage.fillPassAndEmail(USER_PASSWORD_2, email);
adminUserPage.addGroup(BPMN_USER_GROUP);
adminUserPage.clickSaveButton();
adminUserPage.waitForVisibilityOf(adminUserPage.filterPanel);
adminUserPage.searchUser(name);
assertEquals(1, adminUserPage.getListOfLastNamesFromTable().size());
assertEquals(1, adminUserPage.getListOfFirstNamesFromTable().size());
assertEquals(1, adminUserPage.getListOfMiddleNamesFromTable().size());
assertNotEquals(oldName, adminUserPage.getListOfLastNamesFromTable().get(0).getText());
assertNotEquals(oldName, adminUserPage.getListOfFirstNamesFromTable().get(0).getText());
assertNotEquals(oldName, adminUserPage.getListOfMiddleNamesFromTable().get(0).getText());
assertTrue(EXECUTION_MANAGER.hasUserByData(name, email));
adminUserPage.clickOnUserInTable(name);
assertEquals(1, adminUserPage.getListOfGroupsFromTable().size());
assertEquals(BPMN_USER_GROUP, adminUserPage.getListOfGroupsFromTable().get(0).getText());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void deleteUser(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
adminUserPage.deleteUser();
assertTrue(adminUserPage.getListOfLastNamesFromTable().isEmpty());
assertTrue(adminUserPage.getListOfFirstNamesFromTable().isEmpty());
assertTrue(adminUserPage.getListOfMiddleNamesFromTable().isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void attachRemoveGroup(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertTrue(adminUserPage.getListOfGroupsFromTable().isEmpty());
adminUserPage.clickEditButton();
assertFalse(adminUserPage.getListOfAvailableGroupsToAdd().isEmpty());
assertTrue(adminUserPage.getListOfAddedGroups().isEmpty());
adminUserPage.addGroup(BPMN_ADMIN_GROUP);
assertFalse(adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd()).contains(BPMN_ADMIN_GROUP));
assertEquals(BPMN_ADMIN_GROUP, adminUserPage.getListOfAddedGroups().get(0).getText());
assertEquals(1, adminUserPage.getListOfAddedGroups().size());
adminUserPage.clickSaveButton();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertEquals(1, adminUserPage.getListOfGroupsFromTable().size());
assertEquals(BPMN_ADMIN_GROUP, adminUserPage.getListOfGroupsFromTable().get(0).getText());
adminUserPage.clickEditButton();
adminUserPage.removeGroup(BPMN_ADMIN_GROUP);
assertTrue(adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd()).contains(BPMN_ADMIN_GROUP));
assertTrue(adminUserPage.getListOfAddedGroups().isEmpty());
adminUserPage.clickSaveButton();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertTrue(adminUserPage.getListOfGroupsFromTable().isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void attachRemoveAllGroups(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
List<String> groupNamesFromTable = EXECUTION_MANAGER.getGroupNamesFromUserGroup();
List<String> expectedGroups = Arrays.asList(BPMN_ADMIN_GROUP, BPMN_USER_GROUP,
BPMN_SUPERUSER_GROUP);
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertTrue(adminUserPage.getListOfGroupsFromTable().isEmpty());
adminUserPage.clickEditButton();
assertFalse(adminUserPage.getListOfAvailableGroupsToAdd().isEmpty());
assertTrue(adminUserPage.getListOfAddedGroups().isEmpty());
adminUserPage.addAllGroups();
assertTrue(adminUserPage.isAvailableGridEmpty(groupNamesFromTable));
assertFalse(adminUserPage.getListOfAddedGroups().isEmpty());
adminUserPage.removeAllGroups();
assertFalse(adminUserPage.getListOfAvailableGroupsToAdd().isEmpty());
assertTrue(adminUserPage.getListOfAddedGroups().isEmpty());
adminUserPage.addGroup(BPMN_ADMIN_GROUP);
adminUserPage.addGroup(BPMN_USER_GROUP);
adminUserPage.addGroup(BPMN_SUPERUSER_GROUP);
adminUserPage.clickSaveButton();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertEquals(3, adminUserPage.getListOfGroupsFromTable().size());
assertTrue(adminUserPage.getWebElementTexts(adminUserPage.getListOfGroupsFromTable()).containsAll(expectedGroups));
adminUserPage.clickEditButton();
adminUserPage.removeAllGroups();
adminUserPage.clickSaveButton();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertTrue(adminUserPage.getListOfGroupsFromTable().isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void accessLevelGroupVisibility(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUserBindGroups(name, ORGANIZATION_ID, SECURITY_ADMIN_GROUP_ID);
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertTrue(adminUserPage.getWebElementTexts(adminUserPage.getListOfGroupsFromTable()).contains(SECURITY_GROUP));
adminUserPage.clickEditButton();
assertFalse(adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd()).contains(SECURITY_GROUP));
assertTrue(adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups()).contains(SECURITY_GROUP));
adminUserPage.logout();
initQaAdminCredentials();
login(login, password);
adminUserPage = inboxPage.startAdminUser();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
assertFalse(adminUserPage.getWebElementTexts(adminUserPage.getListOfGroupsFromTable()).contains(SECURITY_GROUP));
adminUserPage.clickEditButton();
assertFalse(adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd()).contains(SECURITY_GROUP));
assertFalse(adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups()).contains(SECURITY_GROUP));
}
@Disabled("dev WEBBPMNEXT-7837")
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void userAdminPageGroupsGridSorting(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createUserBindGroups(name, ORGANIZATION_ID, BPMN_ADMIN_GROUP_ID,
BPMN_USER_GROUP_ID, BPMN_SUPERUSER_GROUP_ID);
//User page sorting
List<String> lastNamesNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfLastNamesFromTable());
assertTrue(Comparators.isInOrder(lastNamesNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.USERS_GRID);
List<String> lastNamesReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfLastNamesFromTable());
assertTrue(Comparators.isInOrder(lastNamesReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
List<String> userLinkedGroupsNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfGroupsFromTable());
assertTrue(Comparators.isInOrder(userLinkedGroupsNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.LINKED_GROUPS_GRID);
List<String> userLinkedGroupsReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfGroupsFromTable());
assertTrue(Comparators.isInOrder(userLinkedGroupsReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
//Edit user page sorting
adminUserPage.clickEditButton();
List<String> availableToAddGroupsNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd());
assertTrue(Comparators.isInOrder(availableToAddGroupsNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.GROUPS_TO_ADD_GRID);
List<String> availableGroupsToAddReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd());
assertTrue(Comparators.isInOrder(availableGroupsToAddReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
List<String> addedGroupsNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups());
assertTrue(Comparators.isInOrder(addedGroupsNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.ADDED_GROUPS_GRID);
List<String> addedGroupsReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups());
assertTrue(Comparators.isInOrder(addedGroupsReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
//Create user page sorting
adminUserPage.cancelAction();
adminUserPage.clickCreateButton();
List<String> groupsToAddNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd());
assertTrue(Comparators.isInOrder(groupsToAddNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.GROUPS_TO_ADD_GRID);
List<String> groupsToAddReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfAvailableGroupsToAdd());
assertTrue(Comparators.isInOrder(groupsToAddReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
adminUserPage.addAllGroups();
List<String> addedGroupsInCreateFormNatural = adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups());
assertTrue(Comparators.isInOrder(addedGroupsInCreateFormNatural, String.CASE_INSENSITIVE_ORDER),
"Grid wasn't sorted");
adminUserPage.changeUserPageGridsSort(AdminUserPage.UsersPageGrids.ADDED_GROUPS_GRID);
List<String> addedGroupsInCreatedFormReverse = adminUserPage.getWebElementTexts(adminUserPage.getListOfAddedGroups());
assertTrue(Comparators.isInOrder(addedGroupsInCreatedFormReverse, String.CASE_INSENSITIVE_ORDER.reversed()),
"Grid wasn't sorted");
}
private void openBrowserAndAdminPage(Browser browser) {
openBrowserAndLoginForAdmin(browser);
initAdminName();
adminUserPage = inboxPage.startAdminUser();
}
private String randomEmail() {
String random1 = String.valueOf(20000 + (int) (Math.random() * 20000));
String random2 = String.valueOf(20000 + (int) (Math.random() * 20000));
return random1 + "@" + random2 + ".ru";
}
/*@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void addNewOrgToUser(Browser browser) {
openBrowserAndAdminPage(browser);
EXECUTION_MANAGER.createTestOrg(name);
EXECUTION_MANAGER.createUser(name, ORGANIZATION_ID);
organizationPage.clickCreateButton();
organizationPage.waitOrgEditingPageLoading();
organizationPage.fillOrgNameAndCode(name2);
organizationPage.chooseParentOrg(DEFAULT_ORG);
organizationPage.clickSaveButton();
AdminUserPage adminUserPage = inboxPage.startAdminUser();
adminUserPage.searchUser(name);
adminUserPage.clickOnUserInTable(name);
adminUserPage.clickEditButton();
adminUserPage.chooseUserOrganization(name2);
adminUserPage.fillPass(name);
adminUserPage.clickSaveButton();
}
private void openBrowserAndAdminPage(Browser browser) {
openBrowserAndLoginForAdmin(browser);
initAdminName();
name2 = name.substring(0, 3) + "2" + name.substring(3);
name3 = name.substring(0, 3) + "3" + name.substring(3);
organizationPage = inboxPage.startAdminOrganization();
assertFalse(isElementEnabled(DELETE_BUTTON));
}*/
}

View file

@ -1,141 +0,0 @@
package old;
import old.core.BaseTest;
import old.core.Browser;
import org.junit.jupiter.api.AfterEach;
import org.openqa.selenium.By;
import org.openqa.selenium.TimeoutException;
import org.openqa.selenium.support.PageFactory;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import old.page.InboxPage;
import old.page.LoginPage;
import old.page.ProcessesPage;
import old.util.ExecutionManager;
import old.util.PropertyManager;
import java.io.IOException;
import java.util.Properties;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static old.page.BaseComponentPage.getLoginHeaderBy;
import static old.page.BaseComponentPage.getProgressBar;
import static old.util.DataUtil.BASE_PART_FOR_USER;
/**
* @author gulnaz
*/
public abstract class BaseComponentIT extends BaseTest {
protected static final String ACCESS_LEVEL_ID = "a6bf4b31-6648-4095-b269-2a950b548a10";
protected static final String ORGANIZATION_ID = "3516544f-64c5-4883-9047-28bcce74d1be";
protected static final String SECURITY_ADMIN_GROUP_ID = "84c5c1e2-081e-45e1-a874-d6bb232e57ad";
protected static final String BPMN_ADMIN_GROUP_ID = "ddfdc772-7aee-492f-be7d-7e95ea2f45b3";
protected static final String BPMN_USER_GROUP_ID = "62cd890b-99f7-47a8-be60-e330186b17a0";
protected static final String BPMN_SUPERUSER_GROUP_ID = "273d8bbd-0e82-4064-a548-850e9aa61756";
protected static ExecutionManager EXECUTION_MANAGER = new ExecutionManager();
protected InboxPage inboxPage;
protected ProcessesPage processPage;
protected String login;
protected String password;
protected String name;
private Properties config;
final Logger logger = LoggerFactory.getLogger(getClass());
BaseComponentIT() {
super();
initCredentialsConfig();
initCredentials();
}
@AfterEach
public void exit() {
if (processPage != null) {
assertTrue(processPage.thereIsNoError());
}
}
public void openBrowserAndLoginForAdmin(Browser browser) {
initDriver(browser);
initDemoCredentials();
login(login, password);
}
public void openBrowserAndLoginForJbpm(Browser browser) {
initDriver(browser);
initQaAdminCredentials();
login(login, password);
}
private void initCredentialsConfig() {
try {
config = PropertyManager.getProperties();
}
catch (IOException e) {
throw new RuntimeException("Failed to get properties. " + e);
}
}
protected void initCredentials() {
login = config.getProperty("login");
password = config.getProperty("password");
}
protected void initDemoCredentials() {
login = config.getProperty("demo_login");
password = config.getProperty("demo_password");
}
protected void initQaAdminCredentials() {
login = config.getProperty("qa_admin_login");
password = config.getProperty("qa_admin_password");
}
void login(String login, String password) {
WebDriverWait wait = getExplicitWait(getDefaultTimeout());
wait.until(ExpectedConditions.invisibilityOfElementLocated(getProgressBar()));
wait.until(ExpectedConditions.visibilityOfElementLocated(getLoginHeaderBy()));
LoginPage loginPage = PageFactory.initElements(driver, LoginPage.class);
try {
inboxPage = loginPage.login(login, password);
}
catch (TimeoutException e) {
throw new RuntimeException("Failed to login", e);
}
}
void initAdminName() {
initName(BASE_PART_FOR_USER);
}
void initName(String basePart) {
String random = String.valueOf(20000 + (int) (Math.random() * 20000));
name = basePart + "-" + random;
logger.info(name + " record has been initialized");
}
protected boolean isElementEnabled (String xpath){
return driver.findElement(By.xpath(String.format(xpath))).isEnabled();
}
protected LoginPage getLoginPage() {
return PageFactory.initElements(driver, LoginPage.class);
}
public void openBrowserAndLogin(Browser browser) {
initDriver(browser);
login(login, password);
}
protected InboxPage getInboxPage() {
return PageFactory.initElements(driver, InboxPage.class);
}
}

View file

@ -1,322 +0,0 @@
package old;
import java.io.IOException;
import java.net.MalformedURLException;
import java.util.*;
import javax.crypto.SecretKey;
import old.core.Browser;
import old.core.BrowserArgumentProvider;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.security.Keys;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Disabled;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import org.openqa.selenium.Cookie;
import org.openqa.selenium.JavascriptExecutor;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebDriverException;
import org.openqa.selenium.remote.Augmenter;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.openqa.selenium.support.PageFactory;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import old.page.InboxPage;
import old.util.PropertyManager;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static old.page.BaseComponentPage.getLoginHeaderBy;
/**
* @author gulnaz
*/
public class JWTokensIT extends BaseComponentIT {
private static final String SURNAME = "demo";
private static final String SECRET_KEY = "ZjE5ZjMxNmYtODViZC00ZTQ5LWIxZmYtOGEzYzE3Yjc1MDVk}";
private static final SecretKey SIGNING_KEY;
private static final String ACCESS_TOKEN = "Access-token";
private static final String DEMO_GROUP_ID = "22ee608b-dd9d-4633-906d-7c4efca231a0";
private static final String PROCESS_NAME = "test_process";
private static final Logger LOGGER = LoggerFactory.getLogger(JWTokensIT.class);
private static PasswordEncoder passwordEncoder = new BCryptPasswordEncoder(11);
private Properties config;
private WebDriver newDriver;
private Set<Cookie> cookies;
static {
byte[] encodedKey = Base64.getMimeDecoder().decode(SECRET_KEY);
SIGNING_KEY = Keys.hmacShaKeyFor(encodedKey);
}
public JWTokensIT() throws IOException {
super();
config = PropertyManager.getProperties();
}
@AfterEach
public void afterEachTest() {
if (newDriver != null) {
newDriver.close();
}
EXECUTION_MANAGER.deleteTestUser(login);
}
@Override
protected void initCredentials() {
initAdminName();
login = name;
password = login;
String encodedPassword = passwordEncoder.encode(password);
EXECUTION_MANAGER.insertUser(login, encodedPassword, login + "@test.ru", ORGANIZATION_ID,
DEMO_GROUP_ID
);
}
private void pasteDeadAccessToken() {
String deadAccessToken = createDeadAccessToken(config.getProperty("login"));
Cookie cookie = driver.manage().getCookieNamed(ACCESS_TOKEN);
driver.manage().deleteCookie(cookie);
addCookie(driver, cookie, deadAccessToken);
}
private void addCookie(WebDriver driver, Cookie cookie, String value) {
driver.manage().addCookie(
new Cookie.Builder(cookie.getName(), value)
.expiresOn(cookie.getExpiry())
.path(cookie.getPath())
.build()
);
}
private String createDeadAccessToken(String username) {
return Jwts.builder()
.setSubject(username)
.setIssuer("ru.cg.webbpm.components")
.setIssuedAt(new Date(System.currentTimeMillis()))
.setExpiration(
new Date(System.currentTimeMillis() - 3600 * 1000)
)
.signWith(SIGNING_KEY)
.compact();
}
private void reopenApp() throws MalformedURLException {
int attempts = 0;
while (attempts++ < 5) {
try {
newDriver = new Augmenter().augment(new RemoteWebDriver(getGridURL(), options));
break;
}
catch (WebDriverException ignored) {
LOGGER.info("The driver did not start on " + attempts + " attempt");
}
}
newDriver.get(applicationUrl);
cookies.forEach(cookie -> addCookie(newDriver, cookie, cookie.getValue()));
newDriver.get(applicationUrl); // reopen app again
inboxPage = PageFactory.initElements(newDriver, InboxPage.class);
inboxPage.waitForPageLoad();
}
private void initDriverAndLogin(Browser browser) {
initDriver(browser);
login(login, password);
inboxPage.waitForVisibilityOf(inboxPage.adminList);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void refreshPageWithAliveAccessToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.refreshPage();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void goToPageWithAliveAccessToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.startAdminUser();
inboxPage.waitForPageLoad();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void filterWithAliveAccessToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.startAdminUser();
inboxPage.waitForPageLoad();
inboxPage.waitProgressBarNotVisible();
inboxPage.searchUser(SURNAME);
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void refreshPageWithDeadAccessToken(Browser browser) {
initDriverAndLogin(browser);
pasteDeadAccessToken();
inboxPage.refreshPage();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void goToPageWithDeadAccessToken(Browser browser) {
initDriverAndLogin(browser);
pasteDeadAccessToken();
inboxPage.startAdminUser();
inboxPage.waitForPageLoad();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@Disabled("qa WEBBPMNEXT-9052")
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void filterWithDeadAccessToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.startAdminUser();
inboxPage.waitProgressBarNotVisible();
pasteDeadAccessToken();
inboxPage.searchUser(SURNAME);
inboxPage.waitForPageLoad();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void refreshPageWithDeadRefreshToken(Browser browser) {
initDriverAndLogin(browser);
driver.manage().deleteAllCookies();
inboxPage.refreshPage();
assertFalse(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void goToPageWithDeadRefreshToken(Browser browser) {
initDriverAndLogin(browser);
processPage = inboxPage.startProcess(PROCESS_NAME);
processPage.waitForInitializationOf(processPage.exitButton);
driver.manage().deleteAllCookies();
processPage.exitButton.click();
inboxPage.waitForPageLoad();
assertFalse(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void filterWithDeadRefreshToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.startAdminUser();
inboxPage.waitProgressBarNotVisible();
driver.manage().deleteAllCookies();
inboxPage.waitForPageLoad();
inboxPage.searchUser(SURNAME);
inboxPage.waitForPageLoad();
assertFalse(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@Disabled("dev WEBBPMNEXT-9052") //включить после решения задачи
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkTwoAuthorizedUsersCase(Browser browser) {
initDriverAndLogin(browser);
String firstTab = driver.getWindowHandle();
cookies = driver.manage().getCookies();
inboxPage.exitApp();
getExplicitWait(getDefaultTimeout()).until(
ExpectedConditions.visibilityOfElementLocated(getLoginHeaderBy()));
((JavascriptExecutor) driver).executeScript("window.open();");
List<String> windowHandles = new ArrayList<>(driver.getWindowHandles());
driver.switchTo().window(windowHandles.get(1));
driver.get(applicationUrl);
login(login, password);
driver.switchTo().window(firstTab);
driver.get(applicationUrl);
cookies.forEach(cookie -> addCookie(driver, cookie, cookie.getValue()));
pasteDeadAccessToken();
inboxPage.refreshPage();
inboxPage.waitEmailInput();
assertFalse(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void filterWithNoAccessToken(Browser browser) {
initDriverAndLogin(browser);
inboxPage.startAdminUser();
inboxPage.waitProgressBarNotVisible();
driver.manage().deleteCookieNamed(ACCESS_TOKEN);
inboxPage.searchUser(SURNAME);
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void reopenWithAliveAccessToken(Browser browser) throws MalformedURLException {
initDriverAndLogin(browser);
//don't close browser in the end, we'll do that explicitly
setCloseBrowser(false);
cookies = driver.manage().getCookies();
driver.close();
driver = null;
reopenApp();
assertTrue(inboxPage.getEmailInputsFrom(newDriver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void reopenWithDeadAccessToken(Browser browser) throws MalformedURLException {
initDriverAndLogin(browser);
//don't close browser in the end, we'll do that explicitly
setCloseBrowser(false);
pasteDeadAccessToken();
cookies = driver.manage().getCookies();
driver.close();
driver = null;
reopenApp();
assertTrue(inboxPage.getEmailInputsFrom(newDriver).isEmpty());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void refreshWithNoSession(Browser browser) {
initDriverAndLogin(browser);
((JavascriptExecutor) driver).executeScript(
String.format("window.localStorage.clear();")); //clear localStorage
inboxPage.refreshPage();
assertTrue(inboxPage.getEmailInputsFrom(driver).isEmpty());
}
}

View file

@ -1,404 +0,0 @@
package old.core;
import java.time.Duration;
import java.util.List;
import java.util.function.Supplier;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.openqa.selenium.support.PageFactory;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;
/**
* @author evgeny
*/
@SuppressWarnings("UnusedDeclaration")
public abstract class BasePage {
private static final Duration DEFAULT_TIMEOUT = Duration.ofSeconds(20);
private static final int PROGRESS_VISIBILITY_TIMEOUT_MS = 700;
private static final By ERROR = By.xpath("//div[contains(@class, 'toast-error')]");
private static final By INPUT_IS_ACTIVE = By.xpath("//div[contains(@class, 'input-active')]");
protected static final By PROGRESS_BAR = By.xpath("//div[@class='progress']");
protected final WebDriver driver;
protected final String uri;
public BasePage(WebDriver driver, String uri) {
this.driver = driver;
this.uri = uri;
// Check that we're on the right page.
if (!isAtUri(uri))
throw new IllegalStateException("This is not the '" + uri + "' page");
PageFactory.initElements(driver, this);
}
protected Duration getDefaultTimeout() {
return DEFAULT_TIMEOUT;
}
public static By getProgressBar() {
return PROGRESS_BAR;
}
public static By getErrorBy() {
return ERROR;
}
public boolean isAtUri(String uri) {
if (((RemoteWebDriver) driver).getCapabilities().getBrowserName().equalsIgnoreCase("internet explorer")) {
return true;
}
else {
return waitForCorrectUrl(uri, getDefaultTimeout());
}
}
/**
* Ожидание того, что URL текущей страницы содержит определенный текст.
*
* @param uri адрес текущей страницы
* @param timeout timeout ожидания
* @return <code>true</code> при корректном url
*/
private boolean waitForCorrectUrl(String uri, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.urlContains(uri));
}
/**
* Ожидание видимости элемента, присутствующего в DOM.
* Видимость означает не только то, что элемент отобразился, но и то, что высота и ширина элемента больше 0.
*
* @param webElement элемент, который присутствует в DOM
* @param timeout timeout ожидания
* @return веб-элемент, как только он видим
*/
public WebElement waitForVisibilityOf(WebElement webElement, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.visibilityOf(webElement));
}
/**
* Ожидание видимости элемента, присутствующего в DOM.
* Видимость означает не только то, что элемент отобразился, но и то, что высота и ширина элемента больше 0.
*
* @param webElement элемент, который присутствует в DOM
* @return веб-элемент, как только он видим
*/
public WebElement waitForVisibilityOf(WebElement webElement) {
return waitForVisibilityOf(webElement, getDefaultTimeout());
}
/**
* Ожидание появления элемента в DOM и его видимости.
* Видимость означает не только то, что элемент отобразился, но и то, что высота и ширина элемента больше 0.
*
* @param locator локатор, по которому находится элемент
* @param timeout timeout ожидания
* @return веб-элемент, как только он найден и видим
*/
public WebElement waitForVisibilityOfElementLocated(By locator, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.visibilityOfElementLocated(locator));
}
/**
* Ожидание появления элемента в DOM и его видимости.
* Видимость означает не только то, что элемент отобразился, но и то, что высота и ширина элемента больше 0.
*
* @param locator локатор, по которому находится элемент
* @return веб-элемент, как только он найден и видим
*/
public WebElement waitForVisibilityOfElementLocated(By locator) {
return waitForVisibilityOfElementLocated(locator, getDefaultTimeout());
}
/**
* Ожидание появления элемента в DOM и его видимости.
* Видимость означает не только то, что элемент отобразился, но и то, что высота и ширина элемента больше 0.
*
* @param locator локатор, по которому находится элемент
* @param timeout timeout ожидания
* @param sleep длительность между опросами
* @return веб-элемент, как только он найден и видим
*/
public WebElement waitForVisibilityOfElementLocated(By locator, Duration timeout, Duration sleep) {
return new WebDriverWait(driver, timeout, sleep).until(ExpectedConditions.visibilityOfElementLocated(locator));
}
/**
* Ожидание того, что элемент невидим или не представлен в DOM.
*
* @param locator локатор, по которому находится элемент
* @param timeout timeout ожидания
* @return <code>true</code>, когда элемент невидим или не найден в DOM
*/
public boolean waitForInvisibilityOfElementLocated(By locator, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.invisibilityOfElementLocated(locator));
}
/**
* Ожидание того, что элемент невидим или не представлен в DOM.
*
* @param locator локатор, по которому находится элемент
* @return <code>true</code>, когда элемент невидим или не найден в DOM
*/
public boolean waitForInvisibilityOfElementLocated(By locator) {
return waitForInvisibilityOfElementLocated(locator, getDefaultTimeout());
}
/**
* Ожидание того, что элемент больше не прикреплен к DOM
*
* @param webElement проверяемый элемент
* @param timeout timeout ожидания
* @return <code>true</code>, когда элемент больше не прикреплен к DOM
*/
public boolean waitForStalenessOf(WebElement webElement, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.stalenessOf(webElement));
}
/**
* Ожидание того, что элемент больше не прикреплен к DOM
*
* @param webElement проверяемый элемент
* @return <code>true</code>, когда элемент больше не прикреплен к DOM
*/
public boolean waitForStalenessOf(WebElement webElement) {
return waitForStalenessOf(webElement, getDefaultTimeout());
}
/**
* Ожидание наличия текста в элементе, соответствующем указанному локатору.
*
* @param locator локатор, по которому находится элемент
* @param text проверяемый текст
* @param timeout timeout ожидания
* @return <code>true</code> при наличии текста в элементе
*/
public boolean waitForTextToBePresentInElementLocated(By locator, String text, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.textToBePresentInElementLocated(locator, text));
}
/**
* Ожидание наличия текста в элементе, соответствующем указанному локатору.
*
* @param locator локатор, по которому находится элемент
* @param text проверяемый текст
* @return <code>true</code> при наличии текста в элементе
*/
public boolean waitForTextToBePresentInElementLocated(By locator, String text) {
return waitForTextToBePresentInElementLocated(locator, text, getDefaultTimeout());
}
/**
* Ожидание наличия текста в определенном элементе
*
* @param webElement проверяемый элемент
* @param text проверяемый текст
* @param timeout timeout ожидания
* @return <code>true</code> при наличии текста в элементе
*/
public boolean waitForTextToBePresentInElement(WebElement webElement, String text, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.textToBePresentInElement(webElement, text));
}
/**
* Ожидание наличия текста в определенном элементе
*
* @param webElement проверяемый элемент
* @param text проверяемый текст
* @return <code>true</code> при наличии текста в элементе
*/
public boolean waitForTextToBePresentInElement(WebElement webElement, String text) {
return waitForTextToBePresentInElement(webElement, text, getDefaultTimeout());
}
/**
* Ожидание видимости и доступности присутствующего в DOM элемента для нажатия.
*
* @param webElement проверяемый элемент
* @param timeout timeout ожидания
* @return веб-элемент, как только он доступен для нажатия
*/
public WebElement waitForElementToBeClickable(WebElement webElement, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.elementToBeClickable(webElement));
}
/**
* Ожидание видимости и доступности присутствующего в DOM элемента для нажатия.
*
* @param webElement проверяемый элемент
* @return веб-элемент, как только он доступен для нажатия
*/
public WebElement waitForElementToBeClickable(WebElement webElement) {
return waitForElementToBeClickable(webElement, getDefaultTimeout());
}
/**
* Ожидание появления элемента в DOM, видимости и доступности элемента для нажатия.
*
* @param locator локатор, по которому находится элемент
* @param timeout timeout ожидания
* @return веб-элемент, как только он доступен для нажатия
*/
public WebElement waitForElementToBeClickable(By locator, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.elementToBeClickable(locator));
}
/**
* Ожидание появления элемента в DOM, видимости и доступности элемента для нажатия.
*
* @param locator локатор, по которому находится элемент
* @return веб-элемент, как только он доступен для нажатия
*/
public WebElement waitForElementToBeClickable(By locator) {
return waitForElementToBeClickable(locator, getDefaultTimeout());
}
/**
* Ожидание определенного количества элементов с указанным локатором.
*
* @param locator локатор, по которому находится элемент
* @param number ожидаемое число элементов
* @param timeout timeout ожидания
* @return список элементов с определенным количеством
*/
public List<WebElement> waitForNumberOfElementsToBe(By locator, int number, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.numberOfElementsToBe(locator, number));
}
/**
* Ожидание определенного количества элементов с указанным локатором.
*
* @param locator локатор, по которому находится элемент
* @param number ожидаемое число элементов
* @return список элементов с определенным количеством
*/
public List<WebElement> waitForNumberOfElementsToBe(By locator, int number) {
return waitForNumberOfElementsToBe(locator, number, getDefaultTimeout());
}
/**
* Ожидание того, что как минимум один элемент с указанным локатором представлен на странице.
* Полезно, когда нужно подождать динамический элемент.
*
* @param locator локатор, по которому находится элемент
* @param timeout timeout ожидания
* @return список элементов с указанным локатором
*/
public List<WebElement> waitForPresenceOfAllElementsLocatedBy(By locator, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.presenceOfAllElementsLocatedBy(locator));
}
/**
* Ожидание того, что как минимум один элемент с указанным локатором представлен на странице.
* Полезно, когда нужно подождать динамический элемент.
*
* @param locator локатор, по которому находится элемент
* @return список элементов с указанным локатором
*/
public List<WebElement> waitForPresenceOfAllElementsLocatedBy(By locator) {
return waitForPresenceOfAllElementsLocatedBy(locator, getDefaultTimeout());
}
/**
* Ожидание того, что указзнный элемент содержит атрибут с определенным значением
*
* @param webElement проверяемый элемент
* @param attribute проверяемый атрибут
* @param value проверяемое значение
* @param timeout timeout ожидания
* @return <code>true</code> при наличии значения в атрибуте
*/
public boolean waitForAttributeContains(WebElement webElement, String attribute, String value, Duration timeout) {
return new WebDriverWait(driver, timeout).until(ExpectedConditions.attributeContains(webElement, attribute, value));
}
/**
* Ожидание того, что указзнный элемент содержит атрибут с определенным значением
*
* @param webElement проверяемый элемент
* @param attribute проверяемый атрибут
* @param value проверяемое значение
* @return <code>true</code> при наличии значения в атрибуте
*/
public boolean waitForAttributeContains(WebElement webElement, String attribute, String value) {
return waitForAttributeContains(webElement, attribute, value, getDefaultTimeout());
}
public void sleep(long millis) {
BaseTest.sleep(millis);
}
private void waitForCondition(Supplier<Boolean> condition, long timeOutInMillis) {
long startTime = System.currentTimeMillis();
while (!condition.get()) {
if (System.currentTimeMillis() - startTime >= timeOutInMillis) {
break;
}
sleep(100);
}
}
private void waitProgressBarVisible(long timeOutInMillis) {
waitForCondition(
() -> driver.findElements(PROGRESS_BAR).size() > 0,
timeOutInMillis
);
}
//ожидается, что последний инпут, по которому был клик, выбран
public void waitForInputFieldSelected() {
waitForNumberOfElementsToBe(INPUT_IS_ACTIVE, 1);
}
//ожидается пока пропадет прогресс бар
public void waitProgressBarNotVisible(Duration timeout) {
waitForInvisibilityOfElementLocated(PROGRESS_BAR, timeout);
}
//ожидается пока пропадет прогресс бар с таймаутом по умолчанию
public void waitProgressBarNotVisible() {
waitForInvisibilityOfElementLocated(PROGRESS_BAR, getDefaultTimeout());
}
//проверяется отсутствие ошибок
public boolean thereIsNoError() {
return getErrors().isEmpty();
}
//получить первую ошибку
public WebElement getError() {
return getErrors().get(0);
}
//получить все ошибки
public List<WebElement> getErrors() {
waitForCondition(
() -> driver.findElements(ERROR).size() > 0,
500
);
return driver.findElements(ERROR);
}
//переключиться на другую вкладку
public void goToAnotherTab(String tab) {
waitProgressBarNotVisible(Duration.ofSeconds(10));
driver.switchTo().window(tab);
}
//обновить страницу
public void refreshPage() {
driver.navigate().refresh();
waitProgressBarNotVisible();
}
public void waitForPageLoad() {
waitProgressBarNotVisible();
waitProgressBarVisible(PROGRESS_VISIBILITY_TIMEOUT_MS);
waitProgressBarNotVisible();
}
}

View file

@ -1,273 +0,0 @@
package old.core;
import java.io.File;
import java.io.IOException;
import java.lang.reflect.Method;
import java.net.MalformedURLException;
import java.net.URL;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.time.Duration;
import java.time.Instant;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.HashMap;
import java.util.List;
import java.util.Optional;
import java.util.TimeZone;
import java.util.logging.Level;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.TestInfo;
import org.junit.jupiter.api.extension.AfterTestExecutionCallback;
import org.junit.jupiter.api.extension.ExtensionContext;
import org.junit.jupiter.api.extension.RegisterExtension;
import org.openqa.selenium.OutputType;
import org.openqa.selenium.TakesScreenshot;
import org.openqa.selenium.TimeoutException;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebDriverException;
import org.openqa.selenium.logging.LogEntry;
import org.openqa.selenium.logging.LogType;
import org.openqa.selenium.logging.LoggingPreferences;
import org.openqa.selenium.remote.AbstractDriverOptions;
import org.openqa.selenium.remote.LocalFileDetector;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.openqa.selenium.support.ui.WebDriverWait;
import static old.core.BasePage.getErrorBy;
import static org.junit.jupiter.api.Assertions.assertTrue;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* @author gulnaz
*/
public abstract class BaseTest {
protected static final String gridUrl;
protected static final String applicationUrl;
private static final Logger LOGGER = LoggerFactory.getLogger(BaseTest.class);
private static final String UNDERSCORE = "_";
private static final Duration DEFAULT_TIMEOUT = Duration.ofSeconds(20);
private static final Duration TIMEOUT = Duration.ofSeconds(3);
private static final int WINDOW_WIDTH = 945;
@RegisterExtension
protected ScreenWatcher screenWatcher = new ScreenWatcher();
protected WebDriver driver;
protected AbstractDriverOptions options;
private boolean closeBrowser = true;
private TestInfo testInfo;
static {
gridUrl = System.getProperty("selenium.grid.url");
applicationUrl = System.getProperty("application.url");
LOGGER.info("application.url: {}", applicationUrl);
LOGGER.info("grid.url: {}", gridUrl);
}
@BeforeEach
void beforeEach(TestInfo testInfo) {
this.testInfo = testInfo;
}
@AfterEach
void tearDown() {
if (closeBrowser && driver != null) {
driver.quit();
}
}
public static void sleep(long millis) {
try {
Thread.sleep(millis);
}
catch (InterruptedException e) {
throw new RuntimeException("Something went wrong...", e);
}
}
public URL getGridURL() throws MalformedURLException {
return new URL(gridUrl);
}
protected void initDriver(Browser browser) {
System.setProperty("webdriver.http.factory", "jdk-http-client");
try {
options = browser.getOptions().newInstance();
}
catch (InstantiationException | IllegalAccessException e) {
throw new RuntimeException("Failed to create capabilities", e);
}
options.setCapability("selenoid:options", new HashMap<String, Object>() {
{
put("enableLog", Boolean.valueOf(System.getProperty("enableLog")));
put("enableVNC", Boolean.valueOf(System.getProperty("enableVNC")));
put("enableVideo", Boolean.valueOf(System.getProperty("enableVideo")));
put("sessionTimeout", "3m");
put("logName", getFileName(testInfo.getTestClass(), testInfo.getTestMethod(), testInfo.getDisplayName() + ".log"));
put("videoName", getFileName(testInfo.getTestClass(), testInfo.getTestMethod(), testInfo.getDisplayName() + ".mp4"));
}
});
if (System.getProperty("enableLog") != null && browser == Browser.CHROME) {
LoggingPreferences logPrefs = new LoggingPreferences();
logPrefs.enable(LogType.BROWSER, Level.ALL);
logPrefs.enable(LogType.CLIENT, Level.ALL);
logPrefs.enable(LogType.DRIVER, Level.ALL);
logPrefs.enable(LogType.PERFORMANCE, Level.ALL);
logPrefs.enable(LogType.PROFILER, Level.ALL);
logPrefs.enable(LogType.SERVER, Level.ALL);
options.setCapability("goog:loggingPrefs", logPrefs);
}
LOGGER.info("try to create RemoteWebDriver, " + testInfo.getDisplayName());
int attempts = 0;
while (attempts++ < 5) {
try {
URL gridUrl = getGridURL();
driver = new RemoteWebDriver(gridUrl, options);
break;
}
catch (WebDriverException ignored) {
LOGGER.info("The driver did not start on " + attempts + " attempt");
}
catch (MalformedURLException e) {
throw new RuntimeException("Invalid grid URL", e);
}
}
if (driver == null) {
throw new RuntimeException("Failed to create driver for " + testInfo.getDisplayName());
}
LOGGER.info("RemoteWebDriver created, " + testInfo.getDisplayName());
// Configure to upload local files to remote Selenium instance
((RemoteWebDriver) driver).setFileDetector(new LocalFileDetector());
driver.manage().window().maximize();
//TODO после обновления selenium (4.9.0 <) необходимо перепроверить maximize()
if (getWindowWidth(driver) < WINDOW_WIDTH) { //.maximize() не срабатывает с первого раза
driver.manage().window().maximize();
}
driver.manage().window().maximize();
driver.get(applicationUrl);
assertTrue(waitForCorrectWindowWidth(),
String.format("browser window size is less than and not equal to as expected: expected - %dpx, actual - %dpx",
WINDOW_WIDTH, driver.manage().window().getSize().getWidth()));
assertTrue(getExplicitWait(TIMEOUT)
.until(ExpectedConditions.invisibilityOfElementLocated(getErrorBy())),
"an error occurred while opening application");
}
private int getWindowWidth(WebDriver webDriver) {
return webDriver.manage().window().getSize().getWidth();
}
protected Duration getDefaultTimeout() {
return DEFAULT_TIMEOUT;
}
protected WebDriverWait getExplicitWait(Duration timeout) {
return new WebDriverWait(driver, timeout);
}
protected void setCloseBrowser(boolean closeBrowser) {
this.closeBrowser = closeBrowser;
}
private boolean waitForCorrectWindowWidth() {
try {
return getExplicitWait(TIMEOUT)
.until(webDriver -> webDriver.manage().window().getSize().getWidth() >= WINDOW_WIDTH);
}
catch (TimeoutException ignored) {
return false;
}
}
private String getFileName(Optional<Class<?>> testClass, Optional<Method> testMethod, String displayName) {
String fileName = "";
if (testClass.isPresent()) {
fileName = testClass.get().getSimpleName() + UNDERSCORE;
}
if (testMethod.isPresent()) {
fileName += testMethod.get().getName() + UNDERSCORE;
}
fileName += displayName;
return fileName;
}
private String getFileName(ExtensionContext context) {
return getFileName(context.getTestClass(), context.getTestMethod(), context.getDisplayName());
}
public class ScreenWatcher implements AfterTestExecutionCallback {
private static final String PATH = "target";
private static final String EXTENSION = "jpg";
private File scrFile;
@Override
public void afterTestExecution(ExtensionContext context) throws Exception {
LOGGER.info("afterTestExecution");
boolean failed = context.getExecutionException().isPresent();
if (!failed) {
if (scrFile != null)
scrFile.delete();
}
else {
LOGGER.info("test failed");
if (driver == null)
return;
saveScreen(getFileName(context));
for (String type : driver.manage().logs().getAvailableLogTypes()) {
List<LogEntry> logEntries = driver.manage().logs().get(type).getAll();
if (logEntries.isEmpty()) {
continue;
}
LOGGER.info("Logging browser messages for type: " + type);
for (LogEntry entry : logEntries) {
LocalDateTime localdateTime = LocalDateTime.ofInstant(Instant.ofEpochMilli(entry.getTimestamp()), TimeZone.getDefault().toZoneId());
String dateTime = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss").format(localdateTime);
LOGGER.warn(dateTime + " " + entry.getLevel() + " " + entry.getMessage());
}
LOGGER.info("Logged browser messages for type: " + type);
}
}
}
public void saveScreen(String fileName) {
try {
TakesScreenshot takesScreenshot = (TakesScreenshot) driver;
scrFile = takesScreenshot.getScreenshotAs(OutputType.FILE);
Path destFile = Paths.get("", PATH, fileName + "." + EXTENSION);
Files.copy(scrFile.toPath(), destFile, StandardCopyOption.REPLACE_EXISTING);
}
catch (IOException e) {
throw new RuntimeException("Failed to capture screen", e);
}
}
}
}

View file

@ -1,28 +0,0 @@
package old.core;
import org.openqa.selenium.remote.AbstractDriverOptions;
import org.openqa.selenium.chrome.ChromeOptions;
import org.openqa.selenium.firefox.FirefoxOptions;
/**
* @author gulnaz
*/
public enum Browser {
CHROME(ChromeOptions.class),
FIREFOX(FirefoxOptions.class);
private final Class<? extends AbstractDriverOptions> options;
Browser(Class<? extends AbstractDriverOptions> options) {
this.options = options;
}
public Class<? extends AbstractDriverOptions> getOptions() {
return options;
}
@Override
public String toString() {
return name().toLowerCase();
}
}

View file

@ -1,24 +0,0 @@
package old.core;
import java.util.stream.Stream;
import org.junit.jupiter.api.extension.ExtensionContext;
import org.junit.jupiter.params.provider.Arguments;
import org.junit.jupiter.params.provider.ArgumentsProvider;
public class BrowserArgumentProvider implements ArgumentsProvider {
@Override
public Stream<? extends Arguments> provideArguments(ExtensionContext context) {
String browsers = System.getProperty("browsers");
if ("all".equals(browsers)) {
return Stream.of(
Arguments.of(Browser.CHROME),
Arguments.of(Browser.FIREFOX));
}
return Stream.of(
Arguments.of(Browser.CHROME));
}
}

View file

@ -1,199 +0,0 @@
package old.page;
import org.openqa.selenium.*;
import java.util.List;
import java.util.stream.Collectors;
import java.time.Duration;
/**
* @author kote
*/
public class AdminGroupPage extends BaseComponentPage {
private static final String AVAILABLE_TO_ADD_TABLE = "//*[@object-name='AvailableRecordsGrid']";
private static final String ADDED_TABLE = "//*[@object-name='LinkFieldDialog']";
private static final String LINKED_ROLE_TABLE = "//*[@object-name='RolesGrid']";
private static final String GROUP_NAMES_TABLE = "//*[@object-name='Grid']";
private static final String ROW_BY_NAME = "//div[@role='row']//div[contains(.,'%s')]";
private static final String CELL_WITH_GROUP_NAME = "//div[@col-id='group$name']//span[contains(text(),'%s')]";
private static final String ROLE_TO_ADD_BY_NAME = AVAILABLE_TO_ADD_TABLE + ROW_BY_NAME;
private static final By LINKED_ROLES_GRID = By.xpath(
LINKED_ROLE_TABLE + "//div[@col-id='role$name']" + EXCLUDE_HEADER);
private static final By ROLES_AVAILABLE_TO_ADD_GRID = By.xpath(
AVAILABLE_TO_ADD_TABLE + "//div[@col-id='role$name']" + EXCLUDE_HEADER);
private static final By ADDED_ROLES_GRID = By.xpath(
ADDED_TABLE + "//div[@role='gridcell']" + EXCLUDE_HEADER + "[@col-id='role$name']");
private static final By GROUP_NAMES_GRID = By.xpath(
GROUP_NAMES_TABLE + "//div[@col-id='role$name']" + EXCLUDE_HEADER);
private static final By GRID_BODY = By.xpath(
"//div[@class='ag-center-cols-container']" + "[//div[@role='row']" + EXCLUDE_HEADER + "]");
private static final By ROLE_TO_ADD_TABLE_HEADER = By.xpath(
AVAILABLE_TO_ADD_TABLE + "//div[@col-id='role$name']" + AG_HEADER);
private static final By ADDED_ROLES_TABLE_HEADER = By.xpath(
ADDED_TABLE + "//div[@col-id='role$name']" + AG_HEADER);
private static final By GROUP_NAMES_TABLE_HEADER = By.xpath(
GROUP_NAMES_TABLE + "//div[@col-id='role$name']" + AG_HEADER);
private static final By LINKED_ROLES_TABLE_HEADER = By.xpath(
LINKED_ROLE_TABLE + "//div[@col-id='role$name']" + AG_HEADER);
public AdminGroupPage(WebDriver browser) {
super(browser, "/#/");
}
public void searchGroup(String groupName) {
waitProgressBarNotVisible();
waitForVisibilityOf(searchField);
typeTextOnAdminFilter(searchField, groupName);
waitForInvisibilityGridDownloader();
}
public void chooseGroup(String groupName) {
searchGroup(groupName);
getListOfGroupsNamesFromTable(groupName).get(0).click();
waitProgressBarNotVisible();
waitForPageLoad();
}
public void deleteGroup() {
waitProgressBarNotVisible();
clickDeleteButton();
clickConfirmButton();
}
public List<WebElement> getListOfGroupsNamesFromTable(String name) {
return driver.findElements(By.xpath(String.format(CELL_WITH_GROUP_NAME, name)));
}
public List<WebElement> getListOfRolesFromLinkedTable() {
return driver.findElements(LINKED_ROLES_GRID);
}
public List<WebElement> getListOfRolesToAdd() {
return driver.findElements(ROLES_AVAILABLE_TO_ADD_GRID);
}
public boolean isGridEmpty() {
try {
waitForInvisibilityOfElementLocated(GRID_BODY, Duration.ofSeconds(5));
return true;
}
catch (TimeoutException t) {
return false;
}
}
/**
* Method to avoid parallel test conflicts.
* <p>
* If the list of roles available to adding is not empty, checks if the list contains only newly
* created roles.
* </p>
*
* @param roleNames list retrieved from the database before the parallel test created a role.
* @return value of {@link Boolean} type.
* <p>
* True - if list of roles available for adding is empty, or contains only newly created roles
* from parallel tests.
* </p>
* <p>
* False - if list of roles available for adding contains values from roleNames list.
* </p>
*/
public boolean isAvailableGridEmpty(List<String> roleNames) {
List<String> possibleParallelAddedRole = getListOfRolesToAdd()
.stream()
.map(WebElement::getText)
.collect(Collectors.toList());
if (possibleParallelAddedRole.isEmpty()) {
return true;
}
else {
return roleNames
.stream()
.noneMatch(possibleParallelAddedRole::contains);
}
}
public void addRole(String roleName, boolean needSort) {
if (needSort) {
waitForVisibilityOfElementLocated(ROLE_TO_ADD_TABLE_HEADER).click();
}
By cell = By.xpath(String.format(ROLE_TO_ADD_BY_NAME, roleName));
waitForVisibilityOfElementLocated(By.xpath(String.format(ROLE_TO_ADD_BY_NAME, roleName))).click();
waitForPageLoad();
clickAddButton();
waitProgressBarNotVisible();
}
public void removeRole(String roleName) {
waitForVisibilityOfElementLocated(By.xpath(String.format(ADDED_TABLE + ROW_BY_NAME, roleName))).click();
clickRemoveButton();
waitProgressBarNotVisible();
}
public void addAllRoles() {
clickAddAllButton();
waitProgressBarNotVisible();
}
public void removeAllRoles() {
clickRemoveAllButton();
waitProgressBarNotVisible();
}
public boolean hasRolesInTable(GroupPageGrids tableName, String... roleNames) {
String table = tableName == GroupPageGrids.ADDED_ROLES_GRID ? ADDED_TABLE :
AVAILABLE_TO_ADD_TABLE;
for (String roleName : roleNames) {
List<WebElement> roles = driver.findElements(By.xpath(table + String.format(ROW_BY_NAME, roleName)));
if (roles.isEmpty()) {
return false;
}
}
return true;
}
public List<WebElement> getListOfAddedRoles() {
return driver.findElements(ADDED_ROLES_GRID);
}
public List<WebElement> getListOfGroupNames() {
return driver.findElements(GROUP_NAMES_GRID);
}
public void bindRole(String roleName) {
waitForVisibilityOf(addButton);
addRole(roleName, false);
waitProgressBarNotVisible();
}
public void typeAndSelectLevel(String level) {
typeTextAndSelectOption("access_level", level, level);
}
public void changeGroupPageGridSort(GroupPageGrids value) {
switch (value) {
case ROLES_TO_ADD_GRID:
driver.findElement(ROLE_TO_ADD_TABLE_HEADER).click();
break;
case LINKED_ROLES_GRID:
driver.findElement(LINKED_ROLES_TABLE_HEADER).click();
break;
case ADDED_ROLES_GRID:
driver.findElement(ADDED_ROLES_TABLE_HEADER).click();
case GROUP_NAMES_GRID:
driver.findElement(GROUP_NAMES_TABLE_HEADER).click();
}
waitForPageLoad();
}
public enum GroupPageGrids {
ADDED_ROLES_GRID,
ROLES_TO_ADD_GRID,
LINKED_ROLES_GRID,
GROUP_NAMES_GRID
}
}

View file

@ -1,92 +0,0 @@
package old.page;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import java.util.List;
import java.time.Duration;
/**
* @author kote
*/
public class AdminOrgPage extends BaseComponentPage {
private static final By CELL_WITH_NAME = By.xpath(
"//*[@object-name='Древовидная таблица']//div[@col-id='name'][not(contains(@class,'ag-header'))]//span[@class='ag-group-value']");
private static final By GRID_BODY =
By.xpath("//div[@class='ag-center-cols-container'][//div[@role='row'][not(contains(@class,'ag-header'))]]");
private static final String PLUS_IN_CELL_WITH_NAME =
"//div[@col-id='name'][//span[contains(text(), '%s')]]//span[@ref='eContracted']";
private static final String CHECKBOX_BY_NAME =
"//div[@col-id='name'][.//span[contains(text(), '%s')]]//div[contains(@class,'ag-selection-checkbox')]";
//Organization Editing Page
@FindBy(xpath = "//*[@object-name='Группа фильтров']//input")
private WebElement searchField;
@FindBy(xpath = "//div[label[span[contains(.,'Наименование')]]]//input")
public WebElement nameField;
@FindBy(xpath = "//div[label[span[contains(.,'Код')]]]//input")
private WebElement codeField;
public AdminOrgPage(WebDriver browser) {
super(browser, "/#/");
}
public void fillOrgNameAndCode(String name) {
typeText(nameField, name);
typeText(codeField, name);
}
public void chooseParentOrg(String parentOrgName) {
typeTextAndSelectOption("Выпадающий список (с возможностью сохранения)", parentOrgName, parentOrgName);
}
public void searchOrg(String name) {
typeTextOnAdminFilter(searchField, name);
waitForInvisibilityGridDownloader();
}
public List<WebElement> getListOfOrganizationsFromTable() {
return driver.findElements(CELL_WITH_NAME);
}
public void clickOnPlusSign(String orgName) {
waitForVisibilityOfElementLocated(By.xpath(String.format(PLUS_IN_CELL_WITH_NAME, orgName))).click();
waitProgressBarNotVisible();
}
public void searchAndClickOnOrg(String name) {
if (driver.findElements(By.xpath(String.format(CHECKBOX_BY_NAME, name))).isEmpty()) {
searchOrg(name);
}
waitForVisibilityOfElementLocated(By.xpath(String.format(CHECKBOX_BY_NAME, name))).click();
waitForPageLoad();
}
public void deleteOrg() {
clickDeleteButton();
confirmAction();
}
public void cancelEditingOrg() {
clickCancelButton();
confirmAction();
}
private void confirmAction() {
clickConfirmButton();
waitProgressBarNotVisible();
waitForPageLoad();
}
public void waitGridEmpty() {
waitForInvisibilityOfElementLocated(GRID_BODY, Duration.ofSeconds(60));
}
public void waitOrgEditingPageLoading() {
waitForPageLoad();
waitForVisibilityOf(nameField);
}
}

View file

@ -1,73 +0,0 @@
package old.page;
import java.util.List;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
public class AdminProcessPage extends BaseComponentPage {
private static final By modalMessage = By.xpath("//div[contains(@class, 'modal-body')][contains(., 'Вы действительно хотите')]");
@FindBy(css = "div[col-id = 'process$start_date']")
private List<WebElement> dates;
private static final String PROCESS_XPATH = "//div[@row-id='%s'][.//div[contains(.,'%s')]]";
public AdminProcessPage(WebDriver browser) {
super(browser, "/#/process/instance");
}
private By getProcessBy(String processId, String processName) {
return By.xpath(String.format(PROCESS_XPATH, processId, processName));
}
public WebElement getProcessFromProcessInstanceTable(String processName, String processId) {
By processLocator = (getProcessBy(processId, processName));
return waitForVisibilityOfElementLocated(processLocator);
}
public boolean isNoProcessFound(String processName, String processId) {
By processLocator = (getProcessBy(processId, processName));
if (!driver.findElements(FIRST_ROW_BY).isEmpty()) {
}
return driver.findElements(processLocator).isEmpty();
}
//прервать процесс
public void stopProcess(String processName, String processId) {
getProcessFromProcessInstanceTable(processName, processId).click();
clickStopButton();
waitForVisibilityOfElementLocated(modalMessage);
clickConfirmButton();
waitForInvisibilityOfElementLocated(modalMessage);
}
//переключиться между вкладками с помощью радиобатона
public void changeRadioTab(String radioButtonTab) {
waitProgressBarNotVisible();
WebElement radioTab = driver.findElement(By.xpath("//label[.//span[contains(.,'" + radioButtonTab + "')]]//input"));
radioTab.click();
waitProgressBarNotVisible();
}
//переключится на вкладку завершенных процессов
public void goToFinishedTab() {
changeRadioTab("Завершенные");
waitForPageLoad();
}
//переключится на вкладку прерванных процессов
public void goToStopedTab() {
changeRadioTab("Прерванные");
waitForPageLoad();
}
public String getDateStringByRowNumber(Integer rowNumber) {
return dates.get(rowNumber).getText();
}
}

View file

@ -1,76 +0,0 @@
package old.page;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import java.util.List;
/**
* @author kote
*/
public class AdminRolePage extends BaseComponentPage {
private static final String CELL_WITH_ROLE_NAME = "//div[@col-id='role$name']//span[contains(text(),'%s')]";
private static final String LINK_GROUP_TABLE = "//*[@object-name='GroupsGrid']";
private static final String ROLE_NAME_TABLE = "//*[@object-name='Grid']";
private static final By LINKED_GROUP_GRID = By.xpath(LINK_GROUP_TABLE + "//div[@col-id='group$name']" + EXCLUDE_HEADER);
private static final By ROLE_NAMES_GRID = By.xpath(ROLE_NAME_TABLE + "//div[@col-id='role$name']" + EXCLUDE_HEADER);
private static final By LINKED_GROUP_GRID_HEADER = By.xpath(LINK_GROUP_TABLE + "//div[@col-id='group$name']" + AG_HEADER);
private static final By ROLE_NAMES_GRID_HEADER = By.xpath(ROLE_NAME_TABLE + "//div[@col-id='role$name']" + AG_HEADER);
public AdminRolePage(WebDriver browser) {
super(browser, "/#/");
}
public void searchRole(String roleName) {
waitProgressBarNotVisible();
waitForVisibilityOf(searchField);
typeTextOnAdminFilter(searchField, roleName);
waitForInvisibilityGridDownloader();
waitForPageLoad();
}
public void chooseRole(String roleName) {
searchRole(roleName);
getListOfRolesNamesFromTable(roleName).get(0).click();
waitForInvisibilityGridDownloader();
}
public void deleteRole() {
waitProgressBarNotVisible();
clickDeleteButton();
clickConfirmButton();
waitProgressBarNotVisible();
}
public List<WebElement> getListOfRolesNamesFromTable(String name) {
return driver.findElements(By.xpath(String.format(CELL_WITH_ROLE_NAME, name)));
}
public List<WebElement> getListOfRoleLinkedGroups() {
return driver.findElements(LINKED_GROUP_GRID);
}
public List<WebElement> getListOfRoles() {
return driver.findElements(ROLE_NAMES_GRID);
}
public void changeRolePageGridSort(RolePageGrids value) {
switch (value) {
case GROUP_NAMES_GRID:
driver.findElement(LINKED_GROUP_GRID_HEADER).click();
break;
case ROLE_NAMES_GRID:
driver.findElement(ROLE_NAMES_GRID_HEADER).click();
break;
}
waitForPageLoad();
}
public enum RolePageGrids {
ROLE_NAMES_GRID,
GROUP_NAMES_GRID
}
}

View file

@ -1,246 +0,0 @@
package old.page;
import org.openqa.selenium.By;
import org.openqa.selenium.Keys;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.interactions.Actions;
import org.openqa.selenium.support.FindBy;
import java.util.List;
import java.util.stream.Collectors;
/**
* @author kote
*/
public class AdminUserPage extends BaseComponentPage {
private static final String TABLE_TO_ADD = "//*[@object-name='AvailableRecordsGrid']";
private static final String TABLE_ADDED = "//*[@object-name='LinkFieldDialog for save']";
private static final String USER_TABLE = "//*[@object-name='Grid']";
private static final String LINK_GROUP_TABLE = "//*[@object-name='DependentGrid']";
private static final String ROW_BY_NAME = "//div[@role='row']//div[contains(.,'%s')]";
private static final By CELL_WITH_LAST_NAME = By.xpath(USER_TABLE + "//div[@col-id='user$lastName']" + EXCLUDE_HEADER);
private static final By CELL_WITH_FIRST_NAME = By.xpath(USER_TABLE + "//div[@col-id='user$firstName']" + EXCLUDE_HEADER);
private static final By CELL_WITH_MIDDLE_NAME = By.xpath(USER_TABLE + "//div[@col-id='user$middleName']" + EXCLUDE_HEADER);
private static final By GROUP_IN_TABLE = By.xpath(LINK_GROUP_TABLE + "//div[@col-id='group$name']" + EXCLUDE_HEADER);
private static final By CELL_WITH_LAST_NAME_HEADER = By.xpath(USER_TABLE + "//div[@col-id='user$lastName']" + AG_HEADER);
private static final By GROUP_IN_TABLE_HEADER = By.xpath(LINK_GROUP_TABLE + "//div[@col-id='group$name']" + AG_HEADER);
private static final By GROUP_TO_ADD_HEADER = By.xpath(TABLE_TO_ADD + "//div[@col-id='group$name']" + AG_HEADER);
private static final By ADDED_GROUPS_HEADER = By.xpath(TABLE_ADDED + "//div[@col-id='group$name']" + AG_HEADER);
private static final By GROUP_TO_ADD = By.xpath(TABLE_TO_ADD + "//div[@col-id='group$name']" + EXCLUDE_HEADER);
private static final By ADDED_GROUPS = By.xpath(TABLE_ADDED + "//div[@role='gridcell']" + EXCLUDE_HEADER + "[@col-id='group$name']");
private static final By LOGOUT_BUTTON = By.xpath("//div[@class ='fa fa-power-off']");
//User Administration Page
@FindBy(xpath = "//*[contains(text(),'Фильтр по пользователям')]")
public WebElement filterPanel;
//User Editing Page
@FindBy(xpath = "//*[@object-name='last-name']//input")
public WebElement lastNameField;
@FindBy(xpath = "//div[@class='logout']//button[contains(@class,'nav-link')]")
public WebElement userMenuButton;
@FindBy(xpath = "//button[contains(.,'Выход')]")
public WebElement exitButton;
@FindBy(xpath = "//*[@object-name='first-name']//input")
private WebElement firstNameField;
@FindBy(xpath = "//*[@object-name='middleName']//input")
private WebElement middleNameField;
@FindBy(xpath = "//*[@object-name='login']//input")
private WebElement loginField;
@FindBy(xpath = "//*[@object-name='last-name']//input")
private WebElement surNameField;
@FindBy(xpath = "//*[@object-name='password']//input")
private WebElement passwordField;
@FindBy(xpath = "//*[@object-name='password-repeat']//input")
private WebElement passwordRepeatField;
@FindBy(xpath = "//*[@object-name='email']//input")
private WebElement emailField;
@FindBy(xpath = "//div[@row-index='0']//div[@col-id='checkbox_uid']")
private List<WebElement> listGroupsToAdd;
public AdminUserPage(WebDriver browser) {
super(browser, "/#/");
}
public void fillUserFullName(String userName) {
typeText(lastNameField, userName);
typeText(firstNameField, userName);
typeText(middleNameField, userName);
}
public void fillUserCredentials(String userName, String userPassword, String userEmail,
String userOrganization, String fullOrganizationName) {
typeText(loginField, userName);
fillPassAndEmail(userPassword, userEmail);
chooseUserOrganization(userOrganization, fullOrganizationName);
}
public void chooseUserOrganization(String userOrganization, String fullOrganizationName) {
typeTextAndSelectOption("org_unit_id", userOrganization, fullOrganizationName);
}
public void chooseUserOrganization(String userOrganization) {
typeTextAndSelectOption("org_unit_id", userOrganization, userOrganization);
}
public void fillPassAndEmail(String userPassword, String userEmail) {
fillPass(userPassword);
typeText(emailField, userEmail);
}
public void fillPass(String userPassword) {
typeText(passwordField, userPassword);
typeText(passwordRepeatField, userPassword);
}
public void searchUser(String userSurName) {
filterPanel.click();
waitForPageLoad();
typeTextOnAdminFilter(surNameField, userSurName);
waitForInvisibilityGridDownloader();
}
public void deleteUser() {
waitProgressBarNotVisible();
clickDeleteButton();
clickConfirmButton();
waitProgressBarNotVisible();
}
public List<WebElement> getListOfLastNamesFromTable() {
return driver.findElements(CELL_WITH_LAST_NAME);
}
public List<WebElement> getListOfFirstNamesFromTable() {
return driver.findElements(CELL_WITH_FIRST_NAME);
}
public List<WebElement> getListOfMiddleNamesFromTable() {
return driver.findElements(CELL_WITH_MIDDLE_NAME);
}
public List<WebElement> getListOfGroupsFromTable() {
return driver.findElements(GROUP_IN_TABLE);
}
public List<WebElement> getListOfAddedGroups() {
return driver.findElements(ADDED_GROUPS);
}
public List<WebElement> getListOfAvailableGroupsToAdd() {
return driver.findElements(GROUP_TO_ADD);
}
public void clickOnUserInTable(String userName) {
driver.findElement(By.xpath(String.format(USER_TABLE + ROW_BY_NAME, userName))).click();
waitForPageLoad();
}
public void addGroup(String groupName) {
waitForVisibilityOfElementLocated(By.xpath(String.format(TABLE_TO_ADD + ROW_BY_NAME, groupName))).click();
clickAddButton();
waitProgressBarNotVisible();
}
public void removeGroup(String groupName) {
waitForVisibilityOfElementLocated(By.xpath(String.format(TABLE_ADDED + ROW_BY_NAME, groupName))).click();
clickRemoveButton();
waitForInvisibilityGridDownloader();
}
public void addAllGroups() {
clickAddAllButton();
waitProgressBarNotVisible();
}
public void removeAllGroups() {
clickRemoveAllButton();
waitProgressBarNotVisible();
}
/**
* Method to avoid parallel test conflicts.
* <p>
* If the list of groups available for adding is not empty, checks if the list contains only newly created groups.
* </p>
*
* @param groupNames list retrieved from the database before the parallel test created a new group.
* Instance of {@link List<String>} type.
*
* @return value of {@link Boolean} type.
* <p>
* True - if list of groups available for adding is empty, or contains only newly created groups from parallel tests.
* </p>
* <p>
* False - if list of groups available for adding contains values from groupNames list.
* </p>
*/
public boolean isAvailableGridEmpty(List<String> groupNames) {
List<String> possibleParallelAddedGroups = getListOfAvailableGroupsToAdd()
.stream()
.map(WebElement::getText)
.collect(Collectors.toList());
if (possibleParallelAddedGroups.isEmpty()) {
return true;
}
else {
return groupNames
.stream()
.noneMatch(possibleParallelAddedGroups::contains);
}
}
public void bindGroup(String roleName) {
changeUserPageGridsSort(UsersPageGrids.GROUPS_TO_ADD_GRID);
//проходим вниз все группы пока не найдем нужную
listGroupsToAdd.get(0).click();
Actions actions = new Actions(driver);
int numberOfScrolls = 10;
while (driver.findElements(By.xpath(String.format(TABLE_TO_ADD + ROW_BY_NAME, roleName)))
.isEmpty() && numberOfScrolls != 0) {
actions.sendKeys(Keys.PAGE_DOWN).perform();
numberOfScrolls--;
}
waitProgressBarNotVisible();
addGroup(roleName);
waitProgressBarNotVisible();
}
public void logout() {
waitProgressBarNotVisible();
userMenuButton.click();
exitButton.click();
}
public void changeUserPageGridsSort(UsersPageGrids value) {
switch (value) {
case USERS_GRID:
driver.findElement(CELL_WITH_LAST_NAME_HEADER).click();
break;
case LINKED_GROUPS_GRID:
driver.findElement(GROUP_IN_TABLE_HEADER).click();
break;
case GROUPS_TO_ADD_GRID:
driver.findElement(GROUP_TO_ADD_HEADER).click();
case ADDED_GROUPS_GRID:
driver.findElement(ADDED_GROUPS_HEADER).click();
break;
}
waitForPageLoad();
}
public enum UsersPageGrids {
USERS_GRID,
LINKED_GROUPS_GRID,
GROUPS_TO_ADD_GRID,
ADDED_GROUPS_GRID
}
}

View file

@ -1,287 +0,0 @@
package old.page;
import org.openqa.selenium.By;
import org.openqa.selenium.JavascriptExecutor;
import org.openqa.selenium.Keys;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.interactions.Actions;
import org.openqa.selenium.support.FindBy;
import org.openqa.selenium.TimeoutException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import old.core.BasePage;
import old.util.ExecutionManager;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.List;
import java.util.stream.Collectors;
import java.time.Duration;
import static org.junit.jupiter.api.Assertions.assertTrue;
public abstract class BaseComponentPage extends BasePage {
private static final By PROGRESS_BAR = By.xpath("//img[contains(@src, 'progress.gif')]");
private static final By NGB_MODAL_WINDOW = By.xpath("//ngb-modal-window");
private static final By LOGIN_HEADER_BY = By.xpath("//h2[contains(.,'Вход')]");
private static final String SELECTIZE_BY_OBJECT_NAME = "//*[@object-name='%s']";
private static final By INPUT_IS_ACTIVE = By.xpath("//div[contains(@class, 'input-active')]");
private static final String DATE_TIME_CREATE_OR_UPDATE =
"//div[@col-id='%s']//span[contains(text(),'%s')]/parent::span/parent::div/parent::div/following-sibling::div[@col-id='%s']//span";
private static final By GRID_PROGRESS_BAR = By.xpath(
"//span[contains(text(), 'Загрузка данных, пожалуйста, подождите.')]");
protected static final By EMAIL_INPUT_BY = By.name("username");
protected static final By FIRST_ROW_BY = By.cssSelector(".ag-center-cols-container [row-index='0']");
protected static final By MODAL_DIALOG_FIRST_ROW_BY = By.cssSelector(
".modal-dialog .ag-center-cols-container [row-index='0']");
protected static final String SELECTIZE_INPUT_BY_OBJECT_NAME = SELECTIZE_BY_OBJECT_NAME + "//input";
protected static final String INPUT_WITH_SELECTED_OPTION = SELECTIZE_BY_OBJECT_NAME + "//div[contains(.,'%s')]";
protected static final String OPTION_TO_SELECT = SELECTIZE_BY_OBJECT_NAME + "//div[@data-selectable][contains(.,'%s')]";
protected static final String SELECTIZE_FULL = SELECTIZE_BY_OBJECT_NAME + "//div[contains(@class, 'full has-items')]";
protected static final String EXCLUDE_HEADER = "[not(contains(@class,'ag-header'))]";
protected static final String AG_HEADER = "[contains(@class,'ag-header')]";
private static final String PAGE_HEADER = "//*[contains(text(),'%s')]";
//Administration Page
@FindBy(xpath = "//*[contains(text(),'Фильтр по пользователям')]")
public WebElement filterPanel;
@FindBy(xpath = "//*[@object-name='last-name']//input")
public WebElement surNameField;
@FindBy(xpath = "//*[@object-name='search']//input")
protected WebElement searchField;
@FindBy(xpath = "//*[@object-name='create-button']//button['Создать']")
protected WebElement createButton;
@FindBy(xpath = "//*[@object-name='edit-button']//button['Редактировать']")
protected WebElement editButton;
@FindBy(xpath = "//*[@object-name='delete-button']//button['Удалить']")
protected WebElement deleteButton;
@FindBy(xpath = "//div[@class='modal-dialog']//button[@test-id='yes-btn']")
protected WebElement confirmButton;
@FindBy(xpath = "//button[contains(.,'Отменить')]")
public WebElement cancelButton;
//Editing/Creating Pages
@FindBy(xpath = "//*[@object-name='name']//input")
public WebElement nameField;
@FindBy(xpath = "//button[contains(.,'Сохранить')]")
public WebElement saveButton;
@FindBy(xpath = "//*[@object-name='Add']//button[text()='>']")
protected WebElement addButton;
@FindBy(xpath = "//*[@object-name='Remove']//button[text()='<']")
protected WebElement removeButton;
@FindBy(xpath = "//*[@object-name='AddAll']//button[text()='>>']")
protected WebElement addAllButton;
@FindBy(xpath = "//*[@object-name='RemoveAll']//button[text()='<<']")
protected WebElement removeAllButton;
@FindBy(xpath = "//button[contains(.,'Прервать')]")
private WebElement stopButton;
final Logger logger = LoggerFactory.getLogger(getClass());
protected static ExecutionManager EXECUTION_MANAGER = new ExecutionManager();
public BaseComponentPage(WebDriver browser, String uri) {
super(browser, uri);
}
@Override
public void waitForPageLoad() {
super.waitForPageLoad();
assertTrue(thereIsNoError());
waitForInvisibilityOfElementLocated(NGB_MODAL_WINDOW);
}
@Override
public void refreshPage() {
driver.navigate().refresh();
waitForPageLoad();
}
public void waitForPageLoadWithoutCheckingForError() {
super.waitForPageLoad();
waitForInvisibilityOfElementLocated(NGB_MODAL_WINDOW);
}
public void doubleClick(WebElement element) {
Actions action = new Actions(driver);
action.doubleClick(element).perform();
}
public void typeText(WebElement input, String text) {
waitForVisibilityOf(input);
input.clear();
input.sendKeys(text);
waitProgressBarNotVisible();
}
protected void typeTextFromJS(WebElement input, String text) {
input.click();
input.clear();
((JavascriptExecutor) driver).executeScript("arguments[0].value='" + text + "';", input);
}
public void typeTextOnAdminFilter(WebElement input, String text) {
typeTextFromJS(input, text);
input.sendKeys(" ");
input.sendKeys(Keys.ENTER);
blur(input);
}
protected String getErrorText(By locator) {
WebElement errorMessage = waitForVisibilityOfElementLocated(locator);
return errorMessage.getText();
}
public String getErrorTextFromPage() {
return getErrorText(getErrorBy());
}
protected void typeTextAndSelectOption(String objectName, String inputText, String optionText) {
WebElement selectize = findElement(
By.xpath(String.format(SELECTIZE_BY_OBJECT_NAME, objectName)));
waitForElementToBeClickable(selectize).click();
WebElement input = findElement(
By.xpath(String.format(SELECTIZE_INPUT_BY_OBJECT_NAME, objectName)));
input.sendKeys(Keys.BACK_SPACE);
typeText(input, inputText);
By optionToSelectBy = By.xpath(String.format(OPTION_TO_SELECT, objectName, optionText));
waitForVisibilityOfElementLocated(optionToSelectBy).click();
waitForInvisibilityOfElementLocated(optionToSelectBy);
waitForVisibilityOfElementLocated(By.xpath(String.format(SELECTIZE_FULL, objectName)));
waitForVisibilityOfElementLocated(By.xpath(String.format(INPUT_WITH_SELECTED_OPTION, objectName, optionText)));
}
public String getLocalDate() {
return LocalDateTime.now().minusHours(3).format(DateTimeFormatter.ofPattern("dd.MM.yyyy"));
}
public WebElement getActionTime(String colId, String name, String сolIdAction) {
return waitForVisibilityOfElementLocated(By.xpath(String.format
(DATE_TIME_CREATE_OR_UPDATE, colId, name, сolIdAction)));
}
public void waitForInitializationOf(WebElement... elements) {
long pageLoadStart = System.currentTimeMillis();
waitForPageLoad();
logger.info("page loaded in " + (System.currentTimeMillis() - pageLoadStart) + " ms");
for (WebElement element : elements) {
long elementVisibilityStart = System.currentTimeMillis();
waitForVisibilityOf(element);
logger.info(element + " became visible in " + (System.currentTimeMillis() - elementVisibilityStart) + " ms");
}
}
// ожидается, что последний инпут, по котрому был клик, выбран
public void waitForInputFieldSelected() {
waitForNumberOfElementsToBe(INPUT_IS_ACTIVE, 1);
}
public static By getProgressBar() {
return PROGRESS_BAR;
}
public static By getLoginHeaderBy() {
return LOGIN_HEADER_BY;
}
public List<String> getWebElementTexts(List<WebElement> elements) {
return elements.stream()
.map(WebElement::getText)
.collect(Collectors.toList());
}
protected WebElement findElement(By by) {
return driver.findElement(by);
}
protected List<WebElement> findElements(By by) {
return driver.findElements(by);
}
public void waitForInvisibilityGridDownloader() {
try {
waitForVisibilityOfElementLocated(GRID_PROGRESS_BAR, Duration.ofMillis(1000));
waitForInvisibilityOfElementLocated(GRID_PROGRESS_BAR);
}
catch (TimeoutException ignored) {
logger.info("progress bar not visible");
}
}
protected void blur(WebElement input) {
((JavascriptExecutor) driver).executeScript("arguments[0].blur()", input);
((JavascriptExecutor) driver).executeScript("document.body.click()");
}
public void cancelAction() {
waitForElementToBeClickable(cancelButton).click();
waitForPageLoad();
clickConfirmButton();
}
public void clickSaveButton() {
waitForElementToBeClickable(saveButton).click();
waitProgressBarNotVisible();
waitForPageLoad();
}
public void clickEditButton() {
waitForElementToBeClickable(editButton).click();
waitForPageLoad();
}
public void clickCreateButton() {
waitForElementToBeClickable(createButton).click();
waitForPageLoad();
}
public void clickDeleteButton() {
waitForElementToBeClickable(deleteButton).click();
waitProgressBarNotVisible();
}
public void clickConfirmButton() {
waitForElementToBeClickable(confirmButton).click();
waitProgressBarNotVisible();
}
public void clickAddButton() {
waitForElementToBeClickable(addButton).click();
waitForPageLoad();
}
public void clickRemoveButton() {
waitForElementToBeClickable(removeButton).click();
waitForPageLoad();
}
public void clickAddAllButton() {
waitForElementToBeClickable(addAllButton).click();
waitForPageLoad();
}
public void clickRemoveAllButton() {
waitForElementToBeClickable(removeAllButton).click();
waitForPageLoad();
}
public void clickCancelButton() {
waitForElementToBeClickable(cancelButton).click();
}
public void clickStopButton() {
waitForElementToBeClickable(stopButton).click();
waitProgressBarNotVisible();
}
public void searchUser(String userSurName) {
filterPanel.click();
waitForPageLoad();
typeTextOnAdminFilter(surNameField, userSurName);
waitForInvisibilityGridDownloader();
}
public void checkTitle(String labelName) {
waitForVisibilityOfElementLocated(By.xpath(String.format(PAGE_HEADER, labelName)));
}
}

View file

@ -1,128 +0,0 @@
package old.page;
import java.time.Duration;
import java.util.List;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import org.openqa.selenium.support.PageFactory;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class InboxPage extends BaseComponentPage {
private static final String XPATH_FOR_MENU_ITEM = "//button[@class='dropdown-item'][contains(.,'%s')]";
private static final By PROCESS_LIST_BY = By.xpath("//div[@id='process-instance-list']");
private static final By PROCESS_DATE_BY = By.xpath("//span[contains(.,'Дата запуска')]");
private static final By MENU_ADMINISTRATION = By.xpath("//button[contains(.,'Администрирование')]");
private static final By START_PAGE = By.xpath("//div[@class='logo']");
@FindBy(xpath = "//button[@id='adminDropdownMenu']")
public WebElement adminList;
@FindBy(xpath = "//div[@class='logout']//button[contains(@class,'nav-link')]")
public WebElement userMenuButton;
@FindBy(xpath = "//button[contains(.,'Выход')]")
public WebElement exitButton;
@FindBy(xpath = "//button[@id='startProcessDropdownMenu']")
private WebElement startButton;
@FindBy(xpath = "//button[@routerlink='/user-management/groups']")
private WebElement groupPage;
@FindBy(xpath = "//button[@routerlink='/user-management/roles']")
private WebElement rolePage;
@FindBy(xpath = "//button[@routerlink='/user-management/users']")
private WebElement userPage;
@FindBy(xpath = "//button[@routerlink='/user-management/org-units']")
private WebElement orgPage;
@FindBy(xpath = "//button[@routerlink='/user-management/authorities']")
private WebElement authoritiesPage;
@FindBy(xpath = "//button[@routerlink='/process/instance']")
private WebElement processPage;
@FindBy(xpath = "//div[@class='user-info']//div[@class='user-fio']")
private WebElement userFIO;
public InboxPage(WebDriver browser) {
super(browser, "/#/");
}
//выход из приложения
public void exitApp() {
waitProgressBarNotVisible();
userMenuButton.click();
exitButton.click();
assertTrue(thereIsNoError());
}
//открыть Экземпляры процессов
public AdminProcessPage openAdminProcessPage() {
waitForPageLoad();
adminList.click();
waitForElementToBeClickable(processPage, Duration.ofSeconds(10));
processPage.click();
waitForPageLoad();
waitForVisibilityOfElementLocated(PROCESS_LIST_BY);
waitForVisibilityOfElementLocated(PROCESS_DATE_BY);
return PageFactory.initElements(driver, AdminProcessPage.class);
}
//начать процесс
public ProcessesPage startProcess(String processName) {
waitForPageLoad();
startButton.click();
By menuItem = By.xpath(String.format(XPATH_FOR_MENU_ITEM, processName));
WebElement process = waitForVisibilityOfElementLocated(menuItem);
process.click();
waitForPageLoad();
return PageFactory.initElements(driver, ProcessesPage.class);
}
public AdminUserPage startAdminUser() {
adminList.click();
userPage.click();
waitForPageLoad();
return PageFactory.initElements(driver, AdminUserPage.class);
}
public AdminGroupPage startAdminGroup() {
adminList.click();
groupPage.click();
waitForPageLoad();
return PageFactory.initElements(driver, AdminGroupPage.class);
}
public AdminRolePage startAdminRole() {
adminList.click();
rolePage.click();
waitForPageLoad();
return PageFactory.initElements(driver, AdminRolePage.class);
}
public AdminOrgPage startAdminOrganization() {
adminList.click();
orgPage.click();
waitForPageLoad();
return PageFactory.initElements(driver, AdminOrgPage.class);
}
public List<WebElement> getListOfAdminPanels() {
return findElements(MENU_ADMINISTRATION);
}
public String getUserFIOFromPage() {
return userFIO.getText();
}
public List<WebElement> getEmailInputsFrom(WebDriver element) {
return element.findElements(EMAIL_INPUT_BY);
}
public void waitEmailInput() {
waitForVisibilityOfElementLocated(EMAIL_INPUT_BY);
}
public boolean startPageDisplay() {
waitForPageLoad();
return waitForVisibilityOfElementLocated(START_PAGE).isDisplayed();
}
}

View file

@ -1,78 +0,0 @@
package old.page;
import java.time.Duration;
import org.openqa.selenium.By;
import org.openqa.selenium.TimeoutException;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import org.openqa.selenium.support.PageFactory;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class LoginPage extends BaseComponentPage {
private static final By ERROR_LOGIN = By.xpath("//div[@class='form-signin']//div[contains(@class,'alert-danger')]");
private static final By TEXT_ERROR_DEPLOY_MESSAGE = By.xpath("//*[contains(., 'Приложение стартует')]");
private static final By LOGIN_PAGE_HEADER = By.xpath("//*[contains(text(), 'Вход')]");
@FindBy(name = "username")
private WebElement emailInput;
@FindBy(name = "password")
private WebElement passwordInput;
@FindBy(css = "button[class='btn btn-primary']")
private WebElement enterButton;
@FindBy(xpath = "//*[contains(text(), 'Забыли пароль?')]")
private WebElement resetPasswordLink;
@FindBy(xpath = "//*[contains(text(), 'Зарегистрироваться')]")
private WebElement registrationLink;
public LoginPage(WebDriver browser) {
super(browser, "/#/login");
}
public void typeLoginPasswordAndEnter(String login, String password) {
waitForVisibilityOfElementLocated(EMAIL_INPUT_BY);
passwordInput.clear();
passwordInput.sendKeys(password);
emailInput.clear();
emailInput.sendKeys(login);
enterButton.click();
}
public InboxPage login(String login, String password) {
typeLoginPasswordAndEnter(login, password);
assertTrue(hasNoErrorOnLoginPage(TEXT_ERROR_DEPLOY_MESSAGE), "Failed to deploy backend");
assertTrue(hasNoErrorOnLoginPage(ERROR_LOGIN), "Failed to login");
waitProgressBarNotVisible();
assertTrue(thereIsNoError());
return PageFactory.initElements(driver, InboxPage.class);
}
private boolean hasNoErrorOnLoginPage(By locator) {
try {
waitForInvisibilityOfElementLocated(locator, Duration.ofSeconds(5));
}
catch (TimeoutException ignored) {
logger.error(getErrorText(locator));
return false;
}
return true;
}
public String getErrorTextFromLoginForm() {
return getErrorText(ERROR_LOGIN);
}
public void goToResetPage() {
waitForVisibilityOfElementLocated(LOGIN_PAGE_HEADER);
resetPasswordLink.click();
}
public void goToRegistPage(){
waitForPageLoad();
registrationLink.click();
}
}

View file

@ -1,43 +0,0 @@
package old.page;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class ProcessesPage extends BaseComponentPage {
private static final String TEXT = "//div[@class='form-group']//*[text()='%s']";
@FindBy(xpath = "//navigation-button[@object-name='NavigationButton']//button[contains(.,'Завершить')]")
public WebElement exitButton;
@FindBy(xpath = "//div[@id='page']")
public WebElement pageID;
public ProcessesPage(WebDriver browser) {
super(browser, "/#/process/");
}
public String getTestProcessText() {
return getWebElementTexts(driver.findElements(By.xpath(String.format(TEXT, "Тестовая страница")))).get(0);
}
//----- different
public String getProcessId() {
String str = driver.getCurrentUrl();
Pattern p = Pattern.compile("process\\/(\\d+)");
Matcher m = p.matcher(str);
m.find();
return m.group(1);
}
public void exitProcess() {
waitForElementToBeClickable(exitButton);
exitButton.click();
waitForPageLoadWithoutCheckingForError();
}
}

View file

@ -1,11 +0,0 @@
package old.util;
/**
* @author gulnaz
*/
public final class DataUtil {
private DataUtil() {
}
public static final String BASE_PART_FOR_USER = "qa";
}

View file

@ -1,508 +0,0 @@
package old.util;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Arrays;
import java.util.List;
import java.util.UUID;
import com.zaxxer.hikari.HikariDataSource;
import org.jooq.DSLContext;
import org.jooq.Table;
import org.jooq.TableField;
import org.jooq.Record;
import org.jooq.conf.RenderNameCase;
import org.jooq.conf.Settings;
import org.jooq.impl.DSL;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.cg.webbpm.modules.database.bean.config.Datasource;
import ru.cg.webbpm.modules.database.impl.data_source.HikariDataSourceFactory;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.LINK_USER_ACCOUNT_USER_GROUP;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.LINK_USER_GROUP_USER_ROLE;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.LINK_USER_ROLE_AUTHORITY;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.ORG_UNIT;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.SIMPLE_CREDENTIALS;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.USER_ACCOUNT;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.USER_ACCOUNT_VERIFICATION;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.USER_GROUP;
import static ru.cg.webbpm.modules.security.api.impl.bean.Tables.USER_ROLE;
/**
* @author gulnaz
*/
public class ExecutionManager {
private static final Logger LOGGER = LoggerFactory.getLogger(ExecutionManager.class);
private static final int POOL_SIZE = 2;
private HikariDataSource testDataSource;
public HikariDataSource securityDataSource;
private DSLContext dslContext;
private Settings settings;
public ExecutionManager() {
LOGGER.info("Execution manager creation");
HikariDataSourceFactory hikariDataSourceFactory = new HikariDataSourceFactory(POOL_SIZE);
testDataSource = hikariDataSourceFactory.createDataSource(getDataSource(DataSourceName.TEST));
securityDataSource = hikariDataSourceFactory.createDataSource(getDataSource(DataSourceName.SECURITY));
securityDataSource.setLeakDetectionThreshold(60000);
settings = new Settings();
settings.setRenderNameCase(RenderNameCase.LOWER);
//TODO enable and change wrong port to right
// jbpmDataSource = hikariDataSourceFactory.createDataSource(getDataSource(DataSourceName.JBPM));
// jbpmDataSource.setMaximumPoolSize(5);
}
public enum DataSourceName {
JBPM,
SECURITY,
TEST
}
public String generateId() {
return UUID.randomUUID().toString();
}
private Datasource getDataSource(DataSourceName dataSourceName) {
String host = System.getenv("HOSTNAME");
String databaseName;
String user;
String password;
Datasource datasource = new Datasource();
switch (dataSourceName) {
case JBPM:
databaseName = System.getenv("DB_JBPM_NAME");
user = System.getenv("DB_JBPM_USERNAME");
password = System.getenv("DB_JBPM_PASSWORD");
break;
case SECURITY:
host = System.getenv("DB_SEC_HOST");
databaseName = System.getenv("DB_SEC_NAME");
user = System.getenv("DB_SEC_USERNAME");
password = System.getenv("DB_SEC_PASSWORD");
break;
case TEST:
host = System.getenv("DB_APP_HOST");
databaseName = System.getenv("DB_APP_NAME");
user = System.getenv("DB_APP_USERNAME");
password = System.getenv("DB_APP_PASSWORD");
break;
default:
throw new IllegalStateException("Unexpected value: " + dataSourceName);
}
datasource.setUrl(String.format("jdbc:postgresql://%s:%s/%s",
host,
System.getenv("DB_PORT"),
databaseName));
datasource.setUser(user);
datasource.setPassword(password);
datasource.setDriverClassName("org.postgresql.Driver");
return datasource;
}
public <R extends Record> int countTableRows(Table<R> table) {
try (Connection connection = testDataSource.getConnection()) {
dslContext = DSL.using(connection);
return dslContext.selectCount()
.from(table)
.fetchOne(0, int.class);
}
catch (SQLException e) {
throw new RuntimeException("Failed to count rows", e);
}
}
public List<String> getGroupNamesFromUserGroup() {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_GROUP)
.fetch()
.getValues(USER_GROUP.NAME);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get group names from user group table", e);
}
}
public String getTokenByUserId(String id) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_ACCOUNT_VERIFICATION)
.where(USER_ACCOUNT_VERIFICATION.USER_ACCOUNT_ID.eq(id))
.fetch()
.getValue(0, USER_ACCOUNT_VERIFICATION.TOKEN);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get token from user_account_verification", e);
}
}
public List<String> getRoleNamesFromUserRole() {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_ROLE)
.fetch()
.getValues(USER_ROLE.NAME);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get roles from user_role table", e);
}
}
public String getUserAccountIdByName(String userName) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_ACCOUNT)
.where(USER_ACCOUNT.FIRST_NAME.eq(userName))
.fetch()
.getValue(0, USER_ACCOUNT.USER_ACCOUNT_ID);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get user_account_id from user_account table", e);
}
}
public String getRoleIdByName(String roleName) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_ROLE)
.where(USER_ROLE.NAME.eq(roleName))
.fetch()
.getValue(0, USER_ROLE.USER_ROLE_ID);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get user_role_id from user_role table", e);
}
}
public String getGroupIdByName(String groupName) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
return dslContext.select()
.from(USER_GROUP)
.where(USER_GROUP.NAME.eq(groupName))
.fetch()
.getValue(0, USER_GROUP.USER_GROUP_ID);
}
catch (SQLException e) {
throw new RuntimeException("Failed to get user_group_id from user_group table", e);
}
}
/*
Queries with security datasource
*/
private <R extends Record> void insertSecurityRecord(Table<R> table,
TableField<R, String> field1, TableField<R, String> field2, TableField<R, String> field3,
String value1, String value2, String value3) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.insertInto(table, field1, field2, field3)
.values(value1, value2, value3)
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete record", e);
}
}
private <R extends Record> void deleteSecurityRecord(Table<R> table, TableField<R, String> field, String value) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.delete(table)
.where(field.eq(value))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete record", e);
}
}
public void insertUser(String username, String password, String email, String orgId, String groupId) {
//TODO SUPPORT-3761
try (Connection connection = securityDataSource.getConnection()) {
String userId = generateId();
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext
.insertInto(USER_ACCOUNT,
USER_ACCOUNT.USER_ACCOUNT_ID, USER_ACCOUNT.USERNAME, USER_ACCOUNT.EMAIL,
USER_ACCOUNT.FIRST_NAME, USER_ACCOUNT.LAST_NAME, USER_ACCOUNT.ORG_UNIT_ID)
.values(userId, username, email, username, username, orgId),
dslContext
.insertInto(SIMPLE_CREDENTIALS,
SIMPLE_CREDENTIALS.USER_ACCOUNT_ID, SIMPLE_CREDENTIALS.PASSWORD)
.values(userId, password),
dslContext.insertInto(LINK_USER_ACCOUNT_USER_GROUP, LINK_USER_ACCOUNT_USER_GROUP.LINK_USER_ACCOUNT_USER_GROUP_ID,
LINK_USER_ACCOUNT_USER_GROUP.USER_ACCOUNT_ID, LINK_USER_ACCOUNT_USER_GROUP.USER_GROUP_ID)
.values(generateId(), userId, groupId))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to insert user", e);
}
}
public void deleteTestOrg(String orgName) {
deleteSecurityRecord(ORG_UNIT, ORG_UNIT.NAME, orgName);
}
public void createTestOrg(String orgName) {
insertSecurityRecord(ORG_UNIT, ORG_UNIT.ID, ORG_UNIT.NAME, ORG_UNIT.CODE, generateId(), orgName, orgName);
}
public void createParentAndChildOrgs(String orgName1, String orgName2) {
try (Connection connection = securityDataSource.getConnection()) {
String parentOrgId = generateId();
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext.insertInto(ORG_UNIT, ORG_UNIT.ID, ORG_UNIT.NAME, ORG_UNIT.CODE)
.values(parentOrgId, orgName1, orgName1),
dslContext.insertInto(ORG_UNIT, ORG_UNIT.ID, ORG_UNIT.NAME, ORG_UNIT.CODE, ORG_UNIT.PARENT_ID)
.values(generateId(), orgName2, orgName2, parentOrgId))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to create organizations", e);
}
}
public void deleteTestUser(String userName) {
deleteSecurityRecord(USER_ACCOUNT, USER_ACCOUNT.FIRST_NAME, userName);
}
public void createUser(String username, String organizationID) {
String userAccountId = generateId();
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext
.insertInto(USER_ACCOUNT,
USER_ACCOUNT.USER_ACCOUNT_ID, USER_ACCOUNT.USERNAME, USER_ACCOUNT.EMAIL,
USER_ACCOUNT.FIRST_NAME, USER_ACCOUNT.LAST_NAME, USER_ACCOUNT.MIDDLE_NAME,
USER_ACCOUNT.ORG_UNIT_ID)
.values(userAccountId, username, username + "@test.com", username, username, username, organizationID),
dslContext
.insertInto(SIMPLE_CREDENTIALS,
SIMPLE_CREDENTIALS.USER_ACCOUNT_ID, SIMPLE_CREDENTIALS.PASSWORD)
.values(userAccountId, username))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to create user", e);
}
}
public void createGroupBindRoles(String groupName, String accessLevel, String... roles) {
String groupId = generateId();
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.insertInto(USER_GROUP, USER_GROUP.NAME, USER_GROUP.USER_GROUP_ID, USER_GROUP.ACCESS_LEVEL_ID)
.values(groupName, groupId, accessLevel)
.execute();
Arrays.asList(roles).forEach(role -> bindRoleToGroup(role, groupId));
}
catch (SQLException e) {
throw new RuntimeException("Failed to create Group");
}
}
public void createRoleBindGroups(String roleName, String... groupIds) {
String userRoleId = generateId();
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.insertInto(USER_ROLE, USER_ROLE.NAME, USER_ROLE.USER_ROLE_ID)
.values(roleName, userRoleId)
.execute();
Arrays.asList(groupIds).forEach(groupId -> bindRoleToGroup(userRoleId, groupId));
}
catch (SQLException e) {
throw new RuntimeException("Failed to create role");
}
}
public void createUserBindGroups(String userName, String organizationID, String... groupIDs) {
String userAccountId = generateId();
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext.insertInto(USER_ACCOUNT, USER_ACCOUNT.USER_ACCOUNT_ID, USER_ACCOUNT.EMAIL,
USER_ACCOUNT.FIRST_NAME,
USER_ACCOUNT.LAST_NAME, USER_ACCOUNT.MIDDLE_NAME, USER_ACCOUNT.ORG_UNIT_ID,
USER_ACCOUNT.USERNAME)
.values(userAccountId, userName + "@test.com", userName, userName, userName,
organizationID, userName),
dslContext.insertInto(SIMPLE_CREDENTIALS, SIMPLE_CREDENTIALS.USER_ACCOUNT_ID,
SIMPLE_CREDENTIALS.PASSWORD)
.values(userAccountId, userName))
.execute();
Arrays.asList(groupIDs).forEach(group -> bindGroupToUser(group, userAccountId));
}
catch (SQLException e) {
throw new RuntimeException("Failed to create user", e);
}
}
private void bindRoleToGroup(String roleId, String groupId) {
String linkUserGroupUserRoleId = generateId();
dslContext.insertInto(LINK_USER_GROUP_USER_ROLE,
LINK_USER_GROUP_USER_ROLE.LINK_USER_GROUP_USER_ROLE_ID,
LINK_USER_GROUP_USER_ROLE.USER_GROUP_ID, LINK_USER_GROUP_USER_ROLE.USER_ROLE_ID)
.values(linkUserGroupUserRoleId, groupId, roleId)
.execute();
}
private void bindGroupToUser(String groupId, String userAccountId) {
String linkUserAccountUserGroupId = generateId();
dslContext.insertInto(LINK_USER_ACCOUNT_USER_GROUP,
LINK_USER_ACCOUNT_USER_GROUP.LINK_USER_ACCOUNT_USER_GROUP_ID,
LINK_USER_ACCOUNT_USER_GROUP.USER_ACCOUNT_ID,
LINK_USER_ACCOUNT_USER_GROUP.USER_GROUP_ID)
.values(linkUserAccountUserGroupId, userAccountId, groupId)
.execute();
}
public void deleteLinkedRolesFromGroup(String groupId) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.delete(LINK_USER_GROUP_USER_ROLE)
.where(LINK_USER_GROUP_USER_ROLE.USER_ROLE_ID.eq(groupId))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete linked group roles", e);
}
}
public void deleteLinkedGroupsFromRole(String roleId) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.delete(LINK_USER_GROUP_USER_ROLE)
.where(LINK_USER_GROUP_USER_ROLE.USER_ROLE_ID.eq(roleId))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete linked role groups", e);
}
}
public void deleteUserLinkedGroups(String userAccountID) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.delete(LINK_USER_ACCOUNT_USER_GROUP)
.where(LINK_USER_ACCOUNT_USER_GROUP.USER_ACCOUNT_ID.eq(userAccountID))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete linked user groups", e);
}
}
public void deleteTestGroup(String groupName) {
deleteSecurityRecord(USER_GROUP, USER_GROUP.NAME, groupName);
}
public void createTestGroup(String groupName, String accessLevelId) {
insertSecurityRecord(USER_GROUP, USER_GROUP.USER_GROUP_ID, USER_GROUP.NAME, USER_GROUP.ACCESS_LEVEL_ID,
generateId(), groupName, accessLevelId);
}
public void createBindGroupRole(String name, String groupId, String accessLevelId, String roleId) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext.insertInto(USER_GROUP, USER_GROUP.USER_GROUP_ID, USER_GROUP.NAME, USER_GROUP.ACCESS_LEVEL_ID)
.values(groupId, name, accessLevelId),
dslContext.insertInto(USER_ROLE, USER_ROLE.USER_ROLE_ID, USER_ROLE.NAME)
.values(roleId, name),
dslContext.insertInto(LINK_USER_GROUP_USER_ROLE, LINK_USER_GROUP_USER_ROLE.LINK_USER_GROUP_USER_ROLE_ID,
LINK_USER_GROUP_USER_ROLE.USER_GROUP_ID, LINK_USER_GROUP_USER_ROLE.USER_ROLE_ID)
.values(generateId(), groupId, roleId))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to create and bind group with role", e);
}
}
public void deleteUserGroupRole(String name, String groupId, String roleId) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.batch(
dslContext.delete(USER_ACCOUNT)
.where(USER_ACCOUNT.FIRST_NAME.eq(name)),
dslContext.delete(USER_GROUP)
.where(USER_GROUP.USER_GROUP_ID.eq(groupId)),
dslContext.delete(USER_ROLE)
.where(USER_ROLE.USER_ROLE_ID.eq(roleId)))
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to delete user, group, role", e);
}
}
public void linkRoleToAuthority(String roleId, String authorityId) {
insertSecurityRecord(LINK_USER_ROLE_AUTHORITY, LINK_USER_ROLE_AUTHORITY.USER_ROLE_AUTHORITY_ID,
LINK_USER_ROLE_AUTHORITY.USER_ROLE_ID, LINK_USER_ROLE_AUTHORITY.AUTHORITY_ID,
generateId(), roleId, authorityId);
}
public void deleteTestRole(String roleName) {
deleteSecurityRecord(USER_ROLE, USER_ROLE.NAME, roleName);
}
public void createTestRole(String roleName) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
dslContext.insertInto(USER_ROLE, USER_ROLE.USER_ROLE_ID, USER_ROLE.NAME)
.values(generateId(), roleName)
.execute();
}
catch (SQLException e) {
throw new RuntimeException("Failed to create role", e);
}
}
public boolean hasUserByData(String username, String email) {
try (Connection connection = securityDataSource.getConnection()) {
dslContext = DSL.using(connection, settings);
int count = dslContext.selectCount()
.from(USER_ACCOUNT)
.where(USER_ACCOUNT.EMAIL.eq(email))
.and(USER_ACCOUNT.FIRST_NAME.eq(username))
.and(USER_ACCOUNT.LAST_NAME.eq(username))
.and(USER_ACCOUNT.MIDDLE_NAME.eq(username))
.execute();
return count == 1;
}
catch (SQLException e) {
throw new RuntimeException("Failed to fetch user count", e);
}
}
}

View file

@ -1,21 +0,0 @@
package old.util;
import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;
/**
* @author: besedin
*/
public final class PropertyManager {
private static final Properties property = new Properties();
private static final String propFileName = "test.properties";
private PropertyManager() {
}
public static Properties getProperties() throws IOException {
InputStream inputStream = PropertyManager.class.getClassLoader().getResourceAsStream(propFileName);
property.load(inputStream);
return property;
}
}

View file

@ -1,61 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import java.util.Arrays;
/**
* @author kote
*/
public class AuthoritiesPage extends BasePage {
private static final String ARROW_BY_SIBLING_LABEL =
"//span[contains(@class,'ag-row-group')][span[contains(.,'%s')]]//span[contains(@class,'closed')]";
private static final String ACTION_BY_NAME = "//static-column-tree-grid//*[text()='%s']";
private static final String BUTTON_BY_NAME = "//button[contains(.,'%s')]";
private static final String BUTTON_ON_DIALOG_BY_NAME = "//div[@class='modal-body']//button[contains(.,'%s')]";
private static final String MODAL_TITLE_BY_NAME = "//*[@class='modal-title'][contains(.,'%s')]";
private static final String ROLE_BY_NAME = "//static-column-grid//div[@class='ag-cell-wrapper']//span[contains(.,'%s')]";
private static final By COMBOBOX_INPUT = By.xpath(
"//combo-box//div[contains(@class,'selectize-input')]//input");
public AuthoritiesPage(WebDriver browser) {
super(browser, "/#/user-management/authorities");
}
public void openActionTree(String... actions) {
Arrays.asList(actions)
.forEach(action -> waitForElementToBeClickable(getBy(ARROW_BY_SIBLING_LABEL, action)).click());
}
public void clickOnAction(String action) {
waitForElementToBeClickable(getBy(ACTION_BY_NAME, action)).click();
}
public void clickOnButton(String name) {
waitForElementToBeClickable(getBy(BUTTON_BY_NAME, name)).click();
}
public void clickOnButtonOnDialog(String name) {
waitForElementToBeClickable(getBy(BUTTON_ON_DIALOG_BY_NAME, name)).click();
}
public boolean isDialogOpened(String title) {
return isPresent(getBy(MODAL_TITLE_BY_NAME, title));
}
public void selectRole(String value) {
typeAndSelectValue(COMBOBOX_INPUT, value);
}
public void clickOnRole(String role) {
waitForElementToBeClickable(getBy(ROLE_BY_NAME, role)).click();
}
public boolean isRoleOnTheList(String role) {
return isPresent(getBy(ROLE_BY_NAME, role));
}
}

View file

@ -1,65 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
/**
* @author kote
*/
public class OrganizationsPage extends BasePage {
private static final String TEXT_ON_PAGE = "//text//div[contains(.,'%s')]";
private static final String BUTTON_BY_NAME = "//button[contains(.,'%s')]";
private static final String ROW_BY_TEXTS = "//div[@role='row'][.//span[contains(.,'%s')]][.//span[contains(.,'%s')]]";
private static final String ARROW_IN_ROW = ROW_BY_TEXTS + "//span[@ref='eContracted']";
private static final String MODAL_TITLE_BY_NAME = "//*[@class='modal-title'][contains(.,'%s')]";
@FindBy(xpath = "//div[label[span[contains(.,'Наименование')]]]//input")
private WebElement orgName;
@FindBy(xpath = "//div[label[span[contains(.,'Код')]]]//input")
private WebElement orgCode;
@FindBy(xpath = "//combo-box//div[contains(@class,'selectize-input')]")
private WebElement parentOrg;
public OrganizationsPage(WebDriver browser) {
super(browser, "/#/user-management/org-units");
}
public boolean isTitleVisible(String title) {
return isPresent(getBy(TEXT_ON_PAGE, title));
}
public boolean isOrganizationVisible(String name, String code) {
return isPresent(getBy(ROW_BY_TEXTS, name, code));
}
public void clickOnButton(String name) {
waitForElementToBeClickable(getBy(BUTTON_BY_NAME, name)).click();
}
public void clickOnOrganization(String name, String code) {
waitForElementToBeClickable(getBy(ROW_BY_TEXTS, name, code)).click();
}
public void clickOnArrowInParentOrganization(String name, String code) {
waitForElementToBeClickable(getBy(ARROW_IN_ROW, name, code)).click();
}
public void editOrgName(String value) {
editField(orgName, value);
}
public void editOrgCode(String value) {
editField(orgCode, value);
}
public void selectParentOrg(String value) {
clickAndSelectValue(parentOrg, value);
}
public boolean isDialogOpened(String title) {
return isPresent(getBy(MODAL_TITLE_BY_NAME, title));
}
}

View file

@ -1,51 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.WebDriver;
public class ProcessesPage extends BasePage {
private static final String SELECTED_TAB = "//div[@class='radio-content'][@title='%s']";
private static final String TEXT_ON_PAGE = "//text//div[contains(.,'%s')]";
private static final String TAB_INPUT_BY_NAME = "//label[.//span[contains(.,'%s')]]//input";
private static final String BUTTON_BY_NAME = "//button[contains(.,'%s')]";
private static final String LINK_BY_NAME = "//a[@class='nav-link'][contains(.,'%s')]";
private static final String MODAL_TITLE_BY_NAME = "//*[@class='modal-title'][contains(.,'%s')]";
private static final String PROCESS_IN_GRID_BY_ID = "//static-column-grid//div[@row-id='%s']";
public ProcessesPage(WebDriver browser) {
super(browser, "/#/process/instance");
}
public void clickOnButton(String name) {
waitForElementToBeClickable(getBy(BUTTON_BY_NAME, name)).click();
}
public void clickOnLink(String name) {
waitForElementToBeClickable(getBy(LINK_BY_NAME, name)).click();
}
public void clickOnTab(String name) {
waitForElementToBeClickable(getBy(TAB_INPUT_BY_NAME, name)).click();
}
public boolean isTabSelected(String name) {
return isPresent(getBy(SELECTED_TAB, name));
}
public boolean isTitleVisible(String title) {
return isPresent(getBy(TEXT_ON_PAGE, title));
}
public boolean isProcessVisibleInGrid(String processId) {
return isPresent(getBy(PROCESS_IN_GRID_BY_ID, processId));
}
public void clickOnProcessInGrid(String processId) {
waitForElementToBeClickable(getBy(PROCESS_IN_GRID_BY_ID, processId)).click();
}
public boolean isDialogOpened(String title) {
return isPresent(getBy(MODAL_TITLE_BY_NAME, title));
}
}

View file

@ -1,96 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
/**
* @author kote
*/
public class RegistrationPage extends BasePage {
private static final By HEADER = By.xpath("//h2[contains(.,'Регистрация')]");
private static final By PASSWORD_AS_TEXT = By.xpath("//input[@name='password'][@type='text']");
private static final By PASSWORD_AS_SYMBOLS = By.xpath(
"//input[@name='password'][@type='password']");
private static final By REGISTRATION_BUTTON = By.xpath(
"//div[@class='register-btn-box']//button");
private static final By REGISTRATION_ERROR = By.xpath(
"//div[@class='form-register']//div[contains(@class,'alert-danger')]");
private static final String COUNTRY_BY_NAME = "//span[@class='country-name'][contains(.,'%s')]";
@FindBy(xpath = "//a[contains(text(), 'Войти')]")
private WebElement loginLink;
@FindBy(xpath = "//span[@class='arrow-down']")
private WebElement selectCountryArrowButton;
@FindBy(xpath = "//div[@class='input-group-append'][.//i[contains(@class,'eye')]]")
private WebElement passwordEyeButton;
@FindBy(xpath = "//div//input[@name='username']")
private WebElement usernameInput;
@FindBy(xpath = "//div//input[@name='email']")
private WebElement emailInput;
@FindBy(xpath = "//div[contains(label,'Номер телефона')]//input")
private WebElement phoneInput;
@FindBy(xpath = "//div//input[@name='password']")
private WebElement passwordInput;
public RegistrationPage(WebDriver browser) {
super(browser, "/#/registration");
}
public boolean isHeaderVisible() {
return isPresent(HEADER);
}
public void loginLinkClick() {
loginLink.click();
}
public String getMaskForPhone() {
return phoneInput.getAttribute("value");
}
public void selectCountry(String countryName) {
selectCountryArrowButton.click();
waitForVisibilityOfElementLocated(getBy(COUNTRY_BY_NAME, countryName)).click();
}
public void passwordEyeButtonClick() {
passwordEyeButton.click();
}
public boolean isPasswordDisplayedAsText() {
return isPresent(PASSWORD_AS_TEXT);
}
public boolean isPasswordDisplayedAsSymbols() {
return isPresent(PASSWORD_AS_SYMBOLS);
}
public void editUsername(String value) {
editField(usernameInput, value);
}
public void editEmail(String value) {
editField(emailInput, value);
}
public void editPhone(String value) {
editField(phoneInput, value);
}
public void editPassword(String value) {
editField(passwordInput, value);
}
public void registerButtonClick() {
waitForElementToBeClickable(REGISTRATION_BUTTON).click();
}
public String getRegistrationErrorText() {
return waitForVisibilityOfElementLocated(REGISTRATION_ERROR).getText();
}
}

View file

@ -1,58 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.support.FindBy;
/**
* @author kote
*/
public class ResetPasswordPage extends BasePage {
private static final By HEADER = By.xpath("//p[contains(.,'Вспомнили пароль?')]");
private static final By RESET_BUTTON = By.xpath("//div[@class='reset-password-btn-box']//button");
private static final By CHANGE_BUTTON = By.xpath("//button[contains(.,'Изменить пароль')]");
@FindBy(xpath = "//a[contains(text(), 'Войти')]")
private WebElement loginLink;
@FindBy(xpath = "//div//input[@name='email']")
private WebElement emailInput;
@FindBy(xpath = "//div//input[@name='password']")
private WebElement passwordInput;
@FindBy(xpath = "//div//input[@name='confirmPassword']")
private WebElement confirmPasswordInput;
public ResetPasswordPage(WebDriver browser) {
super(browser, "/#/reset-password");
}
public boolean isHeaderVisible() {
return isPresent(HEADER);
}
public void loginLinkClick() {
loginLink.click();
}
public void resetButtonClick() {
waitForElementToBeClickable(RESET_BUTTON).click();
}
public void changeButtonClick() {
waitForElementToBeClickable(CHANGE_BUTTON).click();
}
public void editEmail(String value) {
editField(emailInput, value);
}
public void editPassword(String value) {
editField(passwordInput, value);
}
public void editConfirmPassword(String value) {
editField(confirmPasswordInput, value);
}
}

View file

@ -1,33 +0,0 @@
package pages;
import core.BasePage;
import org.openqa.selenium.WebDriver;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class TestProcessPage extends BasePage {
private static final String PAGE_TITLE_BY_TEXT = "//div[@class='form-group']//*[text()='%s']";
private static final String BUTTON_BY_NAME = "//button[contains(.,'%s')]";
public TestProcessPage(WebDriver browser) {
super(browser, "/#/process/");
}
public boolean isPageTitleVisible(String title) {
return isPresent(getBy(PAGE_TITLE_BY_TEXT, title));
}
public String getProcessId() {
String currentUrl = driver.getCurrentUrl();
Pattern pattern = Pattern.compile("process\\/(\\d+)");
Matcher matcher = pattern.matcher(currentUrl);
matcher.find();
return matcher.group(1);
}
public void clickOnButton(String name) {
waitForElementToBeClickable(getBy(BUTTON_BY_NAME, name)).click();
}
}

View file

@ -1,119 +0,0 @@
package tests;
import core.BaseTest;
import core.Browser;
import core.BrowserArgumentProvider;
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import pages.AuthoritiesPage;
import pages.InboxPage;
import pages.LoginPage;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.openqa.selenium.support.PageFactory.initElements;
/**
* @author kote
*/
public class AuthoritiesIT extends BaseTest {
private static final String ADMINISTRATION = "Администрирование";
private static final String AUTHORITIES = "Безопасность действий";
private static final String ALLOW_FOR_ROLE = "Разрешить для роли";
private static final String BPMN_ACTION = "BPMN";
private static final String ADMIN_ACTION = "ADMIN";
private static final String PROCESS_INSTANCE_ACTION = "PROCESS_INSTANCE";
private static final String LIST_ACTION = "LIST";
private static final PasswordEncoder passwordEncoder = new BCryptPasswordEncoder(11);
private static String generatedName;
public AuthoritiesIT() {
super();
}
@BeforeAll
public static void beforeAll() {
generatedName = generateName("userForAuthorities");
String encodedPassword = passwordEncoder.encode(generatedName);
String groupId = EXECUTION_MANAGER.insertGroupAndLinkedRole(generatedName);
String userAccountId = EXECUTION_MANAGER.insertUser(generatedName, generatedName + "@test.ru", encodedPassword);
EXECUTION_MANAGER.linkGroupToUser(userAccountId, groupId);
}
@AfterAll
public static void afterAll() {
EXECUTION_MANAGER.deleteUserByEmail(generatedName);
EXECUTION_MANAGER.deleteGroupByName(generatedName);
EXECUTION_MANAGER.deleteRoleByName(generatedName);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkPermissionsForRole(Browser browser) {
//check action allowed for a role:
InboxPage inboxPage = loginInAppByAdmin(browser);
assertTrue(inboxPage.pageLoadSuccessfully());
inboxPage.clickOnMenu(ADMINISTRATION);
inboxPage.clickOnSubMenu(AUTHORITIES);
AuthoritiesPage authoritiesPage = initElements(driver, AuthoritiesPage.class);
assertTrue(authoritiesPage.pageLoadSuccessfully());
authoritiesPage.openActionTree(BPMN_ACTION, ADMIN_ACTION, PROCESS_INSTANCE_ACTION);
authoritiesPage.clickOnAction(LIST_ACTION);
assertTrue(authoritiesPage.pageLoadSuccessfully());
authoritiesPage.clickOnButton(ALLOW_FOR_ROLE);
assertTrue(authoritiesPage.isDialogOpened(ALLOW_FOR_ROLE));
authoritiesPage.selectRole(generatedName);
authoritiesPage.clickOnButtonOnDialog("Разрешить");
assertTrue(authoritiesPage.pageLoadSuccessfully());
assertTrue(authoritiesPage.isRoleOnTheList(generatedName));
logout(inboxPage);
LoginPage loginPage = initElements(driver, LoginPage.class);
assertTrue(loginPage.pageLoadSuccessfully());
loginPage.typeLoginPasswordAndEnter(generatedName, generatedName);
assertTrue(inboxPage.pageLoadSuccessfully());
inboxPage.clickOnMenu(ADMINISTRATION);
assertTrue(inboxPage.isSubMenuVisible("Экземпляры процессов"));
//check action prohibited for a role:
logout(inboxPage);
reloginInAppByAdmin();
assertTrue(inboxPage.pageLoadSuccessfully());
inboxPage.clickOnMenu(ADMINISTRATION);
inboxPage.clickOnSubMenu(AUTHORITIES);
assertTrue(authoritiesPage.pageLoadSuccessfully());
authoritiesPage.openActionTree(BPMN_ACTION, ADMIN_ACTION, PROCESS_INSTANCE_ACTION);
authoritiesPage.clickOnAction(LIST_ACTION);
assertTrue(authoritiesPage.pageLoadSuccessfully());
authoritiesPage.clickOnRole(generatedName);
authoritiesPage.clickOnButton("Запретить");
assertTrue(authoritiesPage.isDialogOpened("Подтверждение действия"));
authoritiesPage.clickOnButton("Да");
assertTrue(authoritiesPage.pageLoadSuccessfully());
assertFalse(authoritiesPage.isRoleOnTheList(generatedName));
//todo dev WEBBPMNEXT-9095
/*logout(inboxPage);
assertTrue(loginPage.pageLoadSuccessfully());
loginPage.typeLoginPasswordAndEnter(generatedName, generatedName);
assertTrue(inboxPage.pageLoadSuccessfully());
assertFalse(inboxPage.isMenuVisible(ADMINISTRATION));*/
}
}

View file

@ -1,168 +0,0 @@
package tests;
import core.BaseTest;
import core.Browser;
import core.BrowserArgumentProvider;
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import pages.InboxPage;
import pages.LoginPage;
import pages.RegistrationPage;
import pages.ResetPasswordPage;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.openqa.selenium.support.PageFactory.initElements;
/**
* @author kote
*/
public class LoginIT extends BaseTest {
private static final String PART_FOR_NAME = "userForLogin";
private static final String REG_EMAIL = "qa_new_account@mail.ru";
private static final String RESET_EMAIL = "password_recovery_account@mail.ru";
public LoginIT() {
super();
}
@AfterAll
public static void afterAll() {
EXECUTION_MANAGER.deleteUserByEmail(REG_EMAIL);
EXECUTION_MANAGER.deleteUserByEmail(RESET_EMAIL);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkLoginWithWrongData(Browser browser) {
LoginPage loginPage = openApp(browser);
assertTrue(loginPage.pageLoadSuccessfully());
String wrongData = "wrong_test";
loginPage.typeLoginPasswordAndEnter(wrongData, wrongData);
assertEquals("Неправильный логин или пароль", loginPage.getLoginErrorText());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkDisplayUserFio(Browser browser) {
InboxPage inboxPage = loginInApp(browser);
assertTrue(inboxPage.pageLoadSuccessfully());
inboxPage.clickOnMenu("Пользователь");
assertEquals("Основной-Тестовый Пользователь", inboxPage.getUserFIO());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkTransitionsBetweenForms(Browser browser) {
LoginPage loginPage = openApp(browser);
assertTrue(loginPage.pageLoadSuccessfully());
//check transition to registration page:
loginPage.registrationLinkClick();
RegistrationPage registrationPage = initElements(driver, RegistrationPage.class);
assertTrue(registrationPage.pageLoadSuccessfully());
assertTrue(registrationPage.isHeaderVisible());
//check phone mask:
assertEquals("+7 ", registrationPage.getMaskForPhone());
registrationPage.selectCountry("Albania");
assertEquals("+355 ", registrationPage.getMaskForPhone());
//check password view:
assertTrue(registrationPage.isPasswordDisplayedAsSymbols());
registrationPage.passwordEyeButtonClick();
assertTrue(registrationPage.isPasswordDisplayedAsText());
//check transition to login page from registration page:
registrationPage.loginLinkClick();
assertTrue(loginPage.pageLoadSuccessfully());
assertTrue(loginPage.isHeaderVisible());
//check transition to password recovery page:
loginPage.resetPasswordLinkClick();
ResetPasswordPage resetPasswordPage = initElements(driver, ResetPasswordPage.class);
assertTrue(resetPasswordPage.pageLoadSuccessfully());
assertTrue(resetPasswordPage.isHeaderVisible());
//check transition to login page from password recovery page:
resetPasswordPage.loginLinkClick();
assertTrue(loginPage.pageLoadSuccessfully());
assertTrue(loginPage.isHeaderVisible());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkRegistration(Browser browser) {
LoginPage loginPage = openApp(browser);
assertTrue(loginPage.pageLoadSuccessfully());
loginPage.registrationLinkClick();
RegistrationPage registrationPage = initElements(driver, RegistrationPage.class);
assertTrue(registrationPage.pageLoadSuccessfully());
String logPas = generateName(PART_FOR_NAME);
registrationPage.editUsername(logPas);
registrationPage.editEmail("qa_test@micord.ru");
registrationPage.editPhone("+79999999999");
registrationPage.editPassword(logPas);
registrationPage.registerButtonClick();
registrationPage.waitForPageToLoad();
assertEquals("Пользователь с данным почтовым адресом уже существует",
registrationPage.getRegistrationErrorText());
registrationPage.editEmail(REG_EMAIL);
registrationPage.registerButtonClick();
assertTrue(registrationPage.pageLoadSuccessfully());
String id = EXECUTION_MANAGER.getUserAccountIdByLogin(logPas);
String token = EXECUTION_MANAGER.getTokenByUserAccountId(id);
String link = applicationUrl + "#confirm?link=" + token;
driver.get(link);
registrationPage.loginLinkClick();
assertTrue(loginPage.pageLoadSuccessfully());
loginPage.typeLoginPasswordAndEnter(logPas, logPas);
InboxPage inboxPage = initElements(driver, InboxPage.class);
assertTrue(inboxPage.pageLoadSuccessfully());
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkPasswordRecovery(Browser browser) {
LoginPage loginPage = openApp(browser);
assertTrue(loginPage.pageLoadSuccessfully());
String logPas = generateName(PART_FOR_NAME);
EXECUTION_MANAGER.insertUser(logPas, RESET_EMAIL, logPas);
//здесь создаем пользователя с незакодированным паролем, тк нам не нужно будет по нему логиниться
loginPage.resetPasswordLinkClick();
ResetPasswordPage resetPasswordPage = initElements(driver, ResetPasswordPage.class);
assertTrue(resetPasswordPage.pageLoadSuccessfully());
resetPasswordPage.editEmail(RESET_EMAIL);
resetPasswordPage.resetButtonClick();
assertTrue(resetPasswordPage.pageLoadSuccessfully());
String id = EXECUTION_MANAGER.getUserAccountIdByLogin(logPas);
String token = EXECUTION_MANAGER.getTokenByUserAccountId(id);
String link = applicationUrl + "#new-password?token=" + token;
driver.get(link);
String newPass = generateName("NewPass");
resetPasswordPage.editPassword(newPass);
resetPasswordPage.editConfirmPassword(newPass);
resetPasswordPage.changeButtonClick();
assertTrue(resetPasswordPage.pageLoadSuccessfully());
resetPasswordPage.loginLinkClick();
loginPage.typeLoginPasswordAndEnter(RESET_EMAIL, newPass);
InboxPage inboxPage = initElements(driver, InboxPage.class);
assertTrue(inboxPage.pageLoadSuccessfully());
}
}

View file

@ -1,122 +0,0 @@
package tests;
import core.BaseTest;
import core.Browser;
import core.BrowserArgumentProvider;
import org.junit.jupiter.api.AfterAll;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import pages.InboxPage;
import pages.OrganizationsPage;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.openqa.selenium.support.PageFactory.initElements;
import static org.junit.jupiter.api.Assertions.assertTrue;
/**
* @author kote
*/
public class OrganizationsIT extends BaseTest {
private static final String CREATE = "Создать";
private static final String EDIT = "Редактировать";
private static final String SAVE = "Сохранить";
private static final String PARENT_ORG_NAME = "Управление ЗАГС г. Казани";
private static final String SUBSIDIARY_ORG_NAME = "ЗАГС Советского р-на";
private static final String PART_FOR_CODE = "org_code_";
public OrganizationsIT() {
super();
}
@AfterAll
public static void afterAll() {
EXECUTION_MANAGER.deleteOrganizationByName(PARENT_ORG_NAME);
EXECUTION_MANAGER.deleteOrganizationByName(SUBSIDIARY_ORG_NAME);
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void crudOrganizationAndSubsidiary(Browser browser) {
InboxPage inboxPage = loginInAppByAdmin(browser);
assertTrue(inboxPage.pageLoadSuccessfully());
inboxPage.clickOnMenu("Администрирование");
inboxPage.clickOnSubMenu("Организации");
OrganizationsPage organizationsPage = initElements(driver, OrganizationsPage.class);
assertTrue(organizationsPage.pageLoadSuccessfully());
assertTrue(organizationsPage.isTitleVisible("Администрирование организаций"));
//check create organization:
organizationsPage.clickOnButton(CREATE);
assertTrue(organizationsPage.pageLoadSuccessfully());
organizationsPage.editOrgName(PARENT_ORG_NAME);
String parentOrgCode = generateName(PART_FOR_CODE);
organizationsPage.editOrgCode(parentOrgCode);
organizationsPage.clickOnButton(SAVE);
assertTrue(organizationsPage.pageLoadSuccessfully());
assertTrue(organizationsPage.isOrganizationVisible(PARENT_ORG_NAME, parentOrgCode));
//check create subsidiary:
organizationsPage.clickOnButton(CREATE);
assertTrue(organizationsPage.pageLoadSuccessfully());
organizationsPage.editOrgName(SUBSIDIARY_ORG_NAME);
String subsidiaryOrgCode = generateName(PART_FOR_CODE);
organizationsPage.editOrgCode(subsidiaryOrgCode);
organizationsPage.selectParentOrg(PARENT_ORG_NAME);
organizationsPage.clickOnButton(SAVE);
assertTrue(organizationsPage.pageLoadSuccessfully());
organizationsPage.clickOnArrowInParentOrganization(PARENT_ORG_NAME, parentOrgCode);
assertTrue(organizationsPage.isOrganizationVisible(SUBSIDIARY_ORG_NAME, subsidiaryOrgCode));
//check that a subsidiary cannot be the same as an organization:
organizationsPage.clickOnOrganization(SUBSIDIARY_ORG_NAME, subsidiaryOrgCode);
organizationsPage.clickOnButton(EDIT);
assertTrue(organizationsPage.pageLoadSuccessfully());
organizationsPage.selectParentOrg(SUBSIDIARY_ORG_NAME);
organizationsPage.clickOnButton(SAVE);
organizationsPage.waitForPageToLoad();
assertFalse(organizationsPage.thereIsNoError());
assertTrue(organizationsPage.getErrorText().contains("Обнаружен цикл при попытке сменить родителя"));
//check edit subsidiary:
organizationsPage.selectParentOrg(PARENT_ORG_NAME);
String newSubsidiaryOrgCode = generateName(PART_FOR_CODE);
organizationsPage.editOrgCode(newSubsidiaryOrgCode);
organizationsPage.clickOnButton(SAVE);
assertTrue(organizationsPage.pageLoadSuccessfully());
organizationsPage.clickOnArrowInParentOrganization(PARENT_ORG_NAME, parentOrgCode);
assertTrue(organizationsPage.isOrganizationVisible(SUBSIDIARY_ORG_NAME, newSubsidiaryOrgCode));
assertFalse(organizationsPage.isOrganizationVisible(PARENT_ORG_NAME, subsidiaryOrgCode));
//check edit parent organization:
organizationsPage.clickOnOrganization(PARENT_ORG_NAME, parentOrgCode);
organizationsPage.clickOnButton(EDIT);
assertTrue(organizationsPage.pageLoadSuccessfully());
String newParentOrgCode = generateName(PART_FOR_CODE);
organizationsPage.editOrgCode(newParentOrgCode);
organizationsPage.clickOnButton(SAVE);
assertTrue(organizationsPage.pageLoadSuccessfully());
assertTrue(organizationsPage.isOrganizationVisible(PARENT_ORG_NAME, newParentOrgCode));
assertFalse(organizationsPage.isOrganizationVisible(PARENT_ORG_NAME, parentOrgCode));
organizationsPage.clickOnArrowInParentOrganization(PARENT_ORG_NAME, newParentOrgCode);
assertTrue(organizationsPage.isOrganizationVisible(SUBSIDIARY_ORG_NAME, newSubsidiaryOrgCode));
//check delete parent organization:
organizationsPage.clickOnOrganization(PARENT_ORG_NAME, newParentOrgCode);
organizationsPage.clickOnButton("Удалить");
assertTrue(organizationsPage.isDialogOpened("Подтверждение действия"));
organizationsPage.clickOnButton("Да");
assertTrue(organizationsPage.pageLoadSuccessfully());
assertFalse(organizationsPage.isOrganizationVisible(PARENT_ORG_NAME, newParentOrgCode));
assertFalse(organizationsPage.isOrganizationVisible(SUBSIDIARY_ORG_NAME, newSubsidiaryOrgCode));
}
}

View file

@ -1,104 +0,0 @@
package tests;
import core.BaseTest;
import core.Browser;
import core.BrowserArgumentProvider;
import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.ArgumentsSource;
import pages.InboxPage;
import pages.ProcessesPage;
import pages.TestProcessPage;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.openqa.selenium.support.PageFactory.initElements;
/**
* @author kote
*/
public class ProcessesIT extends BaseTest {
private static final String ADMINISTRATION = "Администрирование";
private static final String PROCESSES_INSTANCES = "Экземпляры процессов";
private static final String COMPLETED = "Завершенные";
private static final String ABORTED = "Прерванные";
private static final String TEST_PROCESS = "test_process";
private static final String TEST_PAGE_TITLE = "Тестовая страница";
public ProcessesIT() {
super();
}
@ParameterizedTest
@ArgumentsSource(BrowserArgumentProvider.class)
public void checkActionsWithProcessesInstances(Browser browser) {
InboxPage inboxPage = loginInAppByAdmin(browser);
assertTrue(inboxPage.pageLoadSuccessfully());
//check start process:
inboxPage.startProcess(TEST_PROCESS);
TestProcessPage testProcessPage = initElements(driver, TestProcessPage.class);
assertTrue(testProcessPage.pageLoadSuccessfully());
assertTrue(testProcessPage.isPageTitleVisible(TEST_PAGE_TITLE));
String processId = testProcessPage.getProcessId();
//check active processes:
inboxPage.clickOnMenu(ADMINISTRATION);
inboxPage.clickOnSubMenu(PROCESSES_INSTANCES);
ProcessesPage processesPage = initElements(driver, ProcessesPage.class);
assertTrue(processesPage.pageLoadSuccessfully());
assertTrue(processesPage.isTitleVisible("Процессы"));
assertTrue(processesPage.isTabSelected("Активные"));
assertTrue(processesPage.isProcessVisibleInGrid(processId));
//check view process instance:
processesPage.clickOnProcessInGrid(processId);
processesPage.clickOnButton("Просмотреть");
assertTrue(processesPage.pageLoadSuccessfully());
assertTrue(processesPage.isTitleVisible("Экземпляр процесса"));
processesPage.clickOnLink("Текст");
assertTrue(processesPage.thereIsNoError());
processesPage.clickOnLink("Изображение");
assertTrue(processesPage.thereIsNoError());
processesPage.clickOnButton("Закрыть");
assertTrue(processesPage.pageLoadSuccessfully());
//check aborted processes:
processesPage.clickOnProcessInGrid(processId);
processesPage.clickOnButton("Прервать");
assertTrue(processesPage.isDialogOpened("Подтверждение действия"));
processesPage.clickOnButton("Да");
assertTrue(processesPage.pageLoadSuccessfully());
assertFalse(processesPage.isProcessVisibleInGrid(processId));
processesPage.clickOnTab(ABORTED);
assertTrue(processesPage.pageLoadSuccessfully());
assertTrue(processesPage.isTabSelected(ABORTED));
assertTrue(processesPage.isProcessVisibleInGrid(processId));
//check complete process:
inboxPage.startProcess(TEST_PROCESS);
assertTrue(testProcessPage.pageLoadSuccessfully());
String newProcessId = testProcessPage.getProcessId();
testProcessPage.clickOnButton("Завершить");
assertTrue(inboxPage.pageLoadSuccessfully());
assertFalse(testProcessPage.isPageTitleVisible(TEST_PAGE_TITLE));
//check completed processes:
inboxPage.clickOnMenu(ADMINISTRATION);
inboxPage.clickOnSubMenu(PROCESSES_INSTANCES);
assertTrue(processesPage.pageLoadSuccessfully());
assertFalse(processesPage.isProcessVisibleInGrid(newProcessId));
processesPage.clickOnTab(COMPLETED);
assertTrue(processesPage.pageLoadSuccessfully());
assertTrue(processesPage.isTabSelected(COMPLETED));
assertTrue(processesPage.isProcessVisibleInGrid(newProcessId));
}
}

View file

@ -1,29 +0,0 @@
# параметр включения/выключения параллельного выполнения тестов.
junit.jupiter.execution.parallel.enabled = true
# протестирована стратегия параллельности fixed и dynamic (оба режима на параллельность запуска тестов не повлияли).
junit.jupiter.execution.parallel.config.strategy = dynamic
# параметр желаемого параллелизма (проверено с разными значениями (1-10), на параллельность запуска тестов не повлияло).
# junit.jupiter.execution.parallel.config.dynamic.factor = 1.0
# параметр максимального размера пула (проверено с разными значениями (1-10), на параллельность запуска тестов не повлияло).
junit.jupiter.execution.parallel.config.dynamic.max-pool-size-factor = 6.0
# параллель внутри класса (настроено последовательно, т.к. параллельно создаётся очередь и падает ошибка Failed to create driver).
junit.jupiter.execution.parallel.mode.default = concurrent
# параллель внутри сьюта
#junit.jupiter.execution.parallel.mode.classes.default = concurrent
# возможные стратегии параллельности dynamic, fixed и custom:
# dynamic - вычисляет желаемый параллелизм на основе количества доступных процессоров / ядер, умноженного на коэф-т dynamic.factor. Настраиваемые значения:
# junit.jupiter.execution.parallel.config.dynamic.factor параметр конфигурации (по умолчанию имеет значение 1) - положительное десятичное число
# junit.jupiter.execution.parallel.config.dynamic.max-pool-size-factor параметр конфигурации можно использовать для ограничения максимального количества потоков
# (по умолчанию 256 + значение junit.jupiter.execution.parallel.config.dynamic.factor, умноженное на количество доступных процессоров / ядер) - положительное десятичное число, должно быть больше или равно 1.0
# fixed - устанавливает закрепленное значение параллелизма с помощью коэф-тов:
# junit.jupiter.execution.parallel.config.fixed.parallelism желаемый параллелизм для fixed стратегии (нет значения по умолчанию) - положительное целое число
# junit.jupiter.execution.parallel.config.fixed.max-pool-size желаемый максимальный размер пула (256 + значение junit.jupiter.execution.parallel.config.fixed.parallelism) - положительное целое число,
# должно быть больше или равно junit.jupiter.execution.parallel.config.fixed.parallelism
# custom - пользовательская реализацию с помощью обязательного junit.jupiter.execution.parallel.config.custom.class.
# Пример класса кастомной настройки: https://github.com/sormuras/junit5-1858-fixed-parallelism/commit/1fb2646711c6d59ad68241822e1a609db417c938#diff-d74841653c5af688ce3524c83cc4cf62bad536c64493e888c208ee2a750b6b88
#
# параметр junit.jupiter.execution.parallel.mode.default настраивает параллельность внутри класса (тесты)
# параметр junit.jupiter.execution.parallel.mode.classes.default настраивает параллельность внутри сьюта (IT классы)
# concurrent - паралльный запуск
# same_thread - последовательный запуск

View file

@ -1,18 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>[%-4level] %msg%n</pattern>
</encoder>
</appender>
<logger name="io.github.bonigarcia" level="DEBUG" />
<logger name="io" level="WARN" />
<logger name="org" level="WARN" />
<logger name="com" level="WARN" />
<root level="INFO">
<appender-ref ref="STDOUT" />
</root>
</configuration>

View file

@ -1,15 +0,0 @@
login = qa_test
password = qa_test
demo_login = demo@example.com
demo_password = demo
qa_admin_login = qa_admin
qa_admin_password = qa_admin
tt_kerberos_url = http://desktop-k0nottv.asd.center.cg:8082/task-tracker
security_ldap_sync_db_url = jdbc:postgresql://185.171.13.99:5432/sec_db_task_tracker_ldap_sync
security_ldap_sync_db_user = sec_user_tt
security_ldap_sync_db_password = sec_user_tt
database_driver = org.postgresql.Driver