[DEV] work onn edge and application right ==> refacto th generation of the right

This commit is contained in:
Edouard DUPIN 2023-04-22 00:31:37 +02:00
parent dd936c2e94
commit 10cd17e594
90 changed files with 1389 additions and 292 deletions

View File

@ -27,7 +27,7 @@
<dependency> <dependency>
<groupId>kangaroo-and-rabbit</groupId> <groupId>kangaroo-and-rabbit</groupId>
<artifactId>archidata</artifactId> <artifactId>archidata</artifactId>
<version>0.3.2</version> <version>0.3.5</version>
</dependency> </dependency>
<!-- testing --> <!-- testing -->
<dependency> <dependency>

View File

@ -12,8 +12,11 @@ import org.kar.karso.api.UserResource;
import org.kar.karso.filter.KarsoAuthenticationFilter; import org.kar.karso.filter.KarsoAuthenticationFilter;
import org.kar.karso.model.Application; import org.kar.karso.model.Application;
import org.kar.karso.model.ApplicationToken; import org.kar.karso.model.ApplicationToken;
import org.kar.karso.model.Right;
import org.kar.karso.model.RightDescription;
import org.kar.karso.model.Settings; import org.kar.karso.model.Settings;
import org.kar.karso.model.UserAuth; import org.kar.karso.model.UserAuth;
import org.kar.karso.util.ConfigVariable;
//import org.kar.archidata.model.Migration; //import org.kar.archidata.model.Migration;
import org.kar.archidata.SqlWrapper; import org.kar.archidata.SqlWrapper;
import org.kar.archidata.catcher.ExceptionCatcher; import org.kar.archidata.catcher.ExceptionCatcher;
@ -38,10 +41,11 @@ public class WebLauncher {
} }
public static void main(String[] args) throws InterruptedException { public static void main(String[] args) throws InterruptedException {
ConfigBaseVariable.bdDatabase = "karso"; ConfigBaseVariable.bdDatabase =
"karso";
try { try {
JWTWrapper.initLocalToken(); JWTWrapper.initLocalToken(ConfigVariable.getUUIDKeyRoot());
} catch (Exception e1) { } catch (Exception e1) {
// TODO Auto-generated catch block // TODO Auto-generated catch block
e1.printStackTrace(); e1.printStackTrace();
@ -57,17 +61,33 @@ public class WebLauncher {
out += SqlWrapper.createTable(UserAuth.class); out += SqlWrapper.createTable(UserAuth.class);
out += SqlWrapper.createTable(Application.class); out += SqlWrapper.createTable(Application.class);
out += SqlWrapper.createTable(ApplicationToken.class); out += SqlWrapper.createTable(ApplicationToken.class);
out += SqlWrapper.createTable(RightDescription.class);
out += SqlWrapper.createTable(Right.class);
// default admin: "karadmin" password: "adminA@666" // default admin: "karadmin" password: "adminA@666"
out += """ out += """
INSERT INTO `user` (`login`, `password`, `email`, `admin`) VALUES INSERT INTO `application` (`id`, `name`, `description`, `redirect`, `redirectDev`, `notification`, `ttl`) VALUES
('karadmin', '0ddcac5ede3f1300a1ce5948ab15112f2810130531d578ab8bc4dc131652d7cf7a3ff6e827eb957bff43bc2c65a6a1d46722e5b3a2343ac3176a33ea7250080b', ('0', 'karso', 'Root SSO interface', 'http://atria-soft/karso', '', '', '666');
""";
out += """
INSERT INTO `user` (`id`, `login`, `password`, `email`, `admin`) VALUES
('0', 'karadmin', '0ddcac5ede3f1300a1ce5948ab15112f2810130531d578ab8bc4dc131652d7cf7a3ff6e827eb957bff43bc2c65a6a1d46722e5b3a2343ac3176a33ea7250080b',
'admin@admin.ZZZ', 1); 'admin@admin.ZZZ', 1);
""";
out += """
INSERT INTO `settings` (`key`, `right`, `type`, `value`) VALUES INSERT INTO `settings` (`key`, `right`, `type`, `value`) VALUES
('SIGN_UP_ENABLE', 'rwr-r-', 'BOOLEAN', 'false'), ('SIGN_UP_ENABLE', 'rwr-r-', 'BOOLEAN', 'false'),
('SIGN_IN_ENABLE', 'rwr-r-', 'BOOLEAN', 'true'), ('SIGN_IN_ENABLE', 'rwr-r-', 'BOOLEAN', 'true'),
('SIGN_UP_FILTER', 'rw----', 'STRING', '.*'), ('SIGN_UP_FILTER', 'rw----', 'STRING', '.*'),
('EMAIL_VALIDATION_REQUIRED', 'rwr-r-', 'BOOLEAN', 'false'); ('EMAIL_VALIDATION_REQUIRED', 'rwr-r-', 'BOOLEAN', 'false');
"""; """;
out += """
INSERT INTO `rightDescription` (`id`, `applicationId`, `key`, `title`, `description`, `type`) VALUES
(0, 0, 'ADMIN', 'Administrator', 'Full administrator Right', 'BOOLEAN');
""";
out += """
INSERT INTO `right` (`applicationId`, `userId`, `rightDescriptionId`, `value`) VALUES
(0, 0, 0, 'true');
""";
//out += SqlWrapper.createTable(Migration.class); //out += SqlWrapper.createTable(Migration.class);
System.out.println(out); System.out.println(out);
@ -123,7 +143,6 @@ public class WebLauncher {
try { try {
server.start(); server.start();
System.out.println("Jersey app started at " + getBaseURI()); System.out.println("Jersey app started at " + getBaseURI());
System.out.println("Press CTRL^C to exit..");
Thread.currentThread().join(); Thread.currentThread().join();
} catch (Exception e) { } catch (Exception e) {
System.out.println("There was an error while starting Grizzly HTTP server."); System.out.println("There was an error while starting Grizzly HTTP server.");

View File

@ -0,0 +1,22 @@
package org.kar.karso;
import org.kar.archidata.util.ConfigBaseVariable;
import org.kar.karso.util.ConfigVariable;
public class WebLauncherEdgeLocal {
private WebLauncherEdgeLocal() {}
public static void main(String[] args) throws InterruptedException {
if (true) {
// for local test:
ConfigBaseVariable.apiAdress = "http://0.0.0.0:15080/karso/api/";
ConfigBaseVariable.dbPort = "3306";
ConfigVariable.edge = "true";
//ConfigBaseVariable.dbType = "sqlite";
//ConfigBaseVariable.dbHost = "./bdd_base.sqlite";
}
WebLauncher.main(args);
}
}

View File

@ -1,13 +1,17 @@
package org.kar.karso.api; package org.kar.karso.api;
import org.kar.archidata.SqlWrapper; import org.kar.archidata.SqlWrapper;
import org.kar.archidata.WhereCondition;
import org.kar.archidata.filter.GenericContext; import org.kar.archidata.filter.GenericContext;
import org.kar.karso.model.*; import org.kar.karso.model.*;
import org.kar.archidata.util.JWTWrapper; import org.kar.archidata.util.JWTWrapper;
import org.kar.archidata.annotation.security.RolesAllowed; import org.kar.archidata.annotation.security.RolesAllowed;
import org.kar.archidata.exception.InputException; import org.kar.archidata.exception.InputException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map;
import jakarta.ws.rs.*; import jakarta.ws.rs.*;
import jakarta.ws.rs.core.Context; import jakarta.ws.rs.core.Context;
@ -22,28 +26,67 @@ public class ApplicationResource {
public ApplicationResource() { public ApplicationResource() {
} }
public List<Long> getUserListOfApplication(Long userId) {
List<Long> out = new ArrayList<>();
List<UserLinkApplication> links = null;
try {
links = SqlWrapper.getsWhere(UserLinkApplication.class,
List.of(
new WhereCondition("user_id", "=", userId),
new WhereCondition("deleted", "=", 0)
), false);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
String result = "SERVER Internal error";
System.out.println(" result: " + result);
return out;
}
for (UserLinkApplication app : links) {
out.add(app.application_id);
}
return out;
}
@GET @GET
@RolesAllowed(value= {"USER", "ADMIN"}) @RolesAllowed(value= {"USER", "ADMIN"})
public List<Application> getApplications() throws Exception { public List<Application> getApplications(@Context SecurityContext sc) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("getApplications"); System.out.println("getApplications");
return SqlWrapper.gets(Application.class, false); // TODO filter with the list of element available in his authorizations ...
List<Application> tmp = SqlWrapper.gets(Application.class, false);
List<Long> regular = this.getUserListOfApplication(gc.userByToken.id);
List<Application> out = new ArrayList<>();
for (Application app : tmp) {
if (regular.indexOf(app.id) != -1) {
out.add(app);
}
}
return out;
} }
@GET @GET
@Path("small") @Path("small")
@RolesAllowed(value= {"USER", "ADMIN"}) @RolesAllowed(value= {"USER", "ADMIN"})
public List<ApplicationSmall> getApplicationsSmall() throws Exception { public List<ApplicationSmall> getApplicationsSmall(@Context SecurityContext sc) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("getApplications"); System.out.println("getApplications");
return SqlWrapper.gets(ApplicationSmall.class, false); List<Application> tmp = SqlWrapper.gets(Application.class, false);
List<Long> regular = this.getUserListOfApplication(gc.userByToken.id);
List<ApplicationSmall> out = new ArrayList<>();
for (Application app : tmp) {
if (regular.indexOf(app.id) != -1) {
out.add(new ApplicationSmall(app.name, app.description, app.redirect));
}
}
return out;
} }
@GET @GET
@Path("get_token") @Path("get_token")
@RolesAllowed(value= {"USER", "ADMIN"}) @RolesAllowed(value= {"USER", "ADMIN"})
public Response getClientToken(@Context SecurityContext sc, @QueryParam("application") String application) { public Response getClientToken(@Context SecurityContext sc, @QueryParam("application") String application) throws Exception {
GenericContext gc = (GenericContext) sc.getUserPrincipal(); GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user); System.out.println("== USER ? " + gc.userByToken);
if (application == null) { if (application == null) {
String result = "Input error missing parameter: 'application'"; String result = "Input error missing parameter: 'application'";
@ -60,7 +103,7 @@ public class ApplicationResource {
Application appl = null; Application appl = null;
try { try {
appl = SqlWrapper.getWhere(Application.class, "name", "=", applicationName); appl = SqlWrapper.getWhere(Application.class, List.of(new WhereCondition("name", "=", applicationName)), false);
} catch (Exception e) { } catch (Exception e) {
// TODO Auto-generated catch block // TODO Auto-generated catch block
e.printStackTrace(); e.printStackTrace();
@ -72,11 +115,64 @@ public class ApplicationResource {
if (appl == null) { if (appl == null) {
String result = "Authentiocate-wrong email/login '" + applicationName + "')"; String result = "Authentiocate-wrong email/login '" + applicationName + "')";
System.out.println(" result: " + result); System.out.println(" result: " + result);
return Response.status(404).entity(result).build(); return Response.status(401).entity(result).build();
} }
// Manage application right here... if (false) {
// the pplication id is not streamed in the application liny in the where elements
String ret = JWTWrapper.generateJWToken(gc.user.id, gc.user.login, "KarAuth", applicationName, appl.ttl); // get the local user:
UserAuth localUser = null;
try {
localUser = SqlWrapper.get(UserAuth.class, gc.userByToken.id);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
String result = "SERVER Internal error";
System.out.println(" result: " + result);
return Response.status(500).entity(result).build();
}
if (localUser == null) {
String result = "Authenticate-wrong results '" + applicationName + "')";
System.out.println(" result: " + result);
return Response.status(401).entity(result).build();
}
System.out.println("Get application list: " + localUser.applications);
if (localUser.applications == null || localUser.applications.indexOf((Long)gc.userByToken.id) == -1) {
String result = "Authenticate impossible ==> application not accessible '" + applicationName + "'";
System.out.println(" result: " + result);
return Response.status(401).entity(result).build();
}
} else {
UserLinkApplication links = null;
try {
links = SqlWrapper.getWhere(UserLinkApplication.class,
List.of(
new WhereCondition("user_id", "=", gc.userByToken.id),
new WhereCondition("deleted", "=", 0),
new WhereCondition("application_id", "=", appl.id)
), false);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
String result = "SERVER Internal error";
System.out.println(" result: " + result);
return Response.status(500).entity(result).build();
}
if (links == null) {
String result = "Authenticate impossible ==> application not accessible '" + applicationName + "'";
System.out.println(" result: " + result);
return Response.status(401).entity(result).build();
}
}
// Get the USER Right
Map<String, Object> applicationRight = RightResource.getUserRight(gc.userByToken.id, appl.id);
if (!applicationRight.containsKey("USER")) {
// If the USER is not override, the system add by default USER
applicationRight.put("USER", true);
}
Map<String, Object> outRight = new HashMap<>();
// we set the right in the under map to manage multiple application group right. and in some application user can see other user or all user of the application
outRight.put(applicationName, applicationRight);
String ret = JWTWrapper.generateJWToken(gc.userByToken.id, gc.userByToken.name, "KarAuth", applicationName, outRight, appl.ttl);
//System.out.println(" ==> generate token: " + ret); //System.out.println(" ==> generate token: " + ret);
String returnAdress = appl.redirect; String returnAdress = appl.redirect;
if (isDev) { if (isDev) {
@ -93,7 +189,7 @@ public class ApplicationResource {
System.out.println("Get log_out()"); System.out.println("Get log_out()");
System.out.println("====================================="); System.out.println("=====================================");
GenericContext gc = (GenericContext) sc.getUserPrincipal(); GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user); System.out.println("== USER ? " + gc.userByToken);
if (application == null) { if (application == null) {
String result = "Input error missing parameter: 'application'"; String result = "Input error missing parameter: 'application'";

View File

@ -0,0 +1,109 @@
package org.kar.karso.api;
import org.kar.archidata.SqlWrapper;
import org.kar.archidata.WhereCondition;
import org.kar.karso.model.Right;
import org.kar.karso.model.RightDescription;
import org.kar.archidata.annotation.security.RolesAllowed;
import jakarta.ws.rs.*;
import jakarta.ws.rs.core.MediaType;
import jakarta.ws.rs.core.Response;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@Path("/right")
@Produces({MediaType.APPLICATION_JSON})
public class RightResource {
public static Object transform(String type, String value) {
if ("BOOLEAN".equals(type)) {
return Boolean.valueOf(value);
} else if ("STRING".equals(type)) {
return value;
} else if ("LONG".equals(type)) {
return Long.valueOf(value);
} else if ("NUMBER".equals(type)) {
return Double.valueOf(value);
} else {
return null;
}
}
public static Map<String, Object> getUserRight(long userId, long applicationId) throws Exception {
Map<String, Object> out = new HashMap<>();
List<RightDescription> rightsDescriptions = SqlWrapper.getsWhere(RightDescription.class,
List.of(
new WhereCondition("applicationId", "=", applicationId),
new WhereCondition("deleted", "=", 0)
));
System.out.println("Get some descriptions: " + rightsDescriptions.size() + " applicationId=" + applicationId);
if (rightsDescriptions != null && rightsDescriptions.size() != 0) {
List<Right> rights = SqlWrapper.getsWhere(Right.class,
List.of(
new WhereCondition("applicationId", "=", applicationId),
new WhereCondition("userId", "=", userId),
new WhereCondition("deleted", "=", 0)
));
System.out.println("Get some user right: " + rights.size() + " userID=" + userId);
if (rights != null && rights.size() != 0) {
for (Right right: rights) {
RightDescription description = rightsDescriptions.stream()
.filter(elem -> right.rightDescriptionId == elem.id)
.findAny()
.orElse(null);
if (description != null) {
out.put(description.key, transform(description.type, right.value));
}
}
} else {
System.out.println("The User have no specific right...");
}
} else {
// the application does not manage right with Karso (normal use-case)
System.out.println("Does not manage Karso right...");
}
return out;
}
@GET
@Path("{id}")
@RolesAllowed("ADMIN")
public static Right getWithId(@PathParam("id") Long id) throws Exception {
return SqlWrapper.get(Right.class, id);
}
@GET
@RolesAllowed("ADMIN")
public List<Right> get() throws Exception {
return SqlWrapper.gets(Right.class, false);
}
@POST
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Right post(String jsonRequest) throws Exception {
return SqlWrapper.insertWithJson(Right.class, jsonRequest);
}
@PUT
@Path("{id}")
@RolesAllowed("ADMIN")
@Consumes(MediaType.APPLICATION_JSON)
public Right put(@PathParam("id") Long id, String jsonRequest) throws Exception {
SqlWrapper.update(Right.class, id, jsonRequest);
return SqlWrapper.get(Right.class, id);
}
@DELETE
@Path("{id}")
@RolesAllowed("ADMIN")
public Response delete(@PathParam("id") Long id) throws Exception {
SqlWrapper.setDelete(Right.class, id);
return Response.ok().build();
}
}

View File

@ -90,7 +90,7 @@ public class SystemConfigResource {
JsonNode value = root.findPath("value"); JsonNode value = root.findPath("value");
res.value = value.asText(); res.value = value.asText();
System.out.println(" update valu : " + res.value); System.out.println("Update value : " + res.value);
SqlWrapper.update(res, res.id, List.of("value")); SqlWrapper.update(res, res.id, List.of("value"));
return Response.status(201).entity("{ \"value\":\"" + res.value + "\"}").build(); return Response.status(201).entity("{ \"value\":\"" + res.value + "\"}").build();
} }

View File

@ -1,7 +1,6 @@
package org.kar.karso.api; package org.kar.karso.api;
import org.kar.archidata.model.GetToken; import org.kar.archidata.model.GetToken;
import org.kar.archidata.model.User;
import org.kar.archidata.SqlWrapper; import org.kar.archidata.SqlWrapper;
import org.kar.archidata.WhereCondition; import org.kar.archidata.WhereCondition;
import org.kar.archidata.annotation.security.PermitAll; import org.kar.archidata.annotation.security.PermitAll;
@ -12,6 +11,9 @@ import org.kar.archidata.exception.SystemException;
import org.kar.archidata.filter.GenericContext; import org.kar.archidata.filter.GenericContext;
import org.kar.karso.model.*; import org.kar.karso.model.*;
import org.kar.karso.util.ConfigVariable; import org.kar.karso.util.ConfigVariable;
import com.fasterxml.jackson.annotation.JsonInclude;
import org.kar.archidata.util.JWTWrapper; import org.kar.archidata.util.JWTWrapper;
import jakarta.ws.rs.*; import jakarta.ws.rs.*;
import jakarta.ws.rs.core.Context; import jakarta.ws.rs.core.Context;
@ -19,7 +21,9 @@ import jakarta.ws.rs.core.MediaType;
import jakarta.ws.rs.core.Response; import jakarta.ws.rs.core.Response;
import jakarta.ws.rs.core.SecurityContext; import jakarta.ws.rs.core.SecurityContext;
import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.security.MessageDigest; import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException; import java.security.NoSuchAlgorithmException;
@ -31,6 +35,18 @@ import java.time.LocalDateTime;
@Produces( MediaType.APPLICATION_JSON) @Produces( MediaType.APPLICATION_JSON)
public class UserResource { public class UserResource {
@JsonInclude(JsonInclude.Include.NON_NULL)
public class UserOut {
public long id;
public String login;
public UserOut(long id, String login) {
super();
this.id = id;
this.login = login;
}
}
public UserResource() { public UserResource() {
} }
@GET @GET
@ -47,6 +63,23 @@ public class UserResource {
return SqlWrapper.get(UserAuthGet.class, userId); return SqlWrapper.get(UserAuthGet.class, userId);
} }
@POST
@Path("{userId}/application/{applicationId}/link")
@RolesAllowed("ADMIN")
public Response linkApplication(@Context SecurityContext sc,
@PathParam("userId") long userId,
@PathParam("applicationId") long applicationId,
boolean data) throws Exception {
System.out.println("Find typeNode");
if (data == true) {
SqlWrapper.addLink(UserAuth.class, userId, "application", applicationId);
} else {
SqlWrapper.removeLink(UserAuth.class, userId, "application", applicationId);
}
return Response.ok(SqlWrapper.get(UserAuth.class, userId)).build();
}
// TODO: check this it might be deprecated ...
@POST @POST
@Path("{id}/set_admin") @Path("{id}/set_admin")
@RolesAllowed("ADMIN") @RolesAllowed("ADMIN")
@ -128,11 +161,11 @@ public class UserResource {
@GET @GET
@Path("me") @Path("me")
@RolesAllowed("USER") @RolesAllowed("USER")
public User getMe(@Context SecurityContext sc) { public UserOut getMe(@Context SecurityContext sc) {
System.out.println("getMe()"); System.out.println("getMe()");
GenericContext gc = (GenericContext) sc.getUserPrincipal(); GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user); System.out.println("== USER ? " + gc.userByToken);
return gc.user; return new UserOut(gc.userByToken.id, gc.userByToken.name);
} }
@POST @POST
@ -141,7 +174,7 @@ public class UserResource {
public Response changePassword(@Context SecurityContext sc, ChangePassword data) throws Exception { public Response changePassword(@Context SecurityContext sc, ChangePassword data) throws Exception {
System.out.println("ChangePassword()"); System.out.println("ChangePassword()");
GenericContext gc = (GenericContext) sc.getUserPrincipal(); GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user); System.out.println("== USER ? " + gc.userByToken);
if(data == null) { if(data == null) {
throw new InputException("data", "No data set..."); throw new InputException("data", "No data set...");
@ -250,8 +283,22 @@ public class UserResource {
@Consumes(MediaType.APPLICATION_JSON) @Consumes(MediaType.APPLICATION_JSON)
public GetToken getToken(DataGetToken data) throws Exception { public GetToken getToken(DataGetToken data) throws Exception {
UserAuth user = checkAuthUser(data.method, data.login, data.time, data.password); UserAuth user = checkAuthUser(data.method, data.login, data.time, data.password);
// at the point the user has been not deleted and not blocked.
// this authentication is valid only for Karso ==> not for the application
int expirationTimeInMinutes = ConfigVariable.getAuthExpirationTime(); int expirationTimeInMinutes = ConfigVariable.getAuthExpirationTime();
String ret = JWTWrapper.generateJWToken(user.id, user.login, "KarAuth", "sso", expirationTimeInMinutes);
// Get the USER Right (Note: by construction KARSO have application ID = 0
Map<String, Object> ssoRight = RightResource.getUserRight(user.id, 0);
if (!ssoRight.containsKey("USER")) {
// If the USER is not override, the system add by default USER
ssoRight.put("USER", true);
}
System.out.println("Get new token with right: " + ssoRight);
Map<String, Object> outRight = new HashMap<>();
String applicationName = "karso";
// we set the right in the under map to manage multiple application group right. and in some application user can see other user or all user of the application
outRight.put(applicationName, ssoRight);
String ret = JWTWrapper.generateJWToken(user.id, user.login, "KarAuth", applicationName, outRight, expirationTimeInMinutes);
// Update last connection: // Update last connection:
UserAuth newUser = new UserAuth(); UserAuth newUser = new UserAuth();

View File

@ -20,7 +20,11 @@ import jakarta.annotation.Priority;
public class KarsoAuthenticationFilter extends AuthenticationFilter { public class KarsoAuthenticationFilter extends AuthenticationFilter {
//curl http://0.0.0.0:15080/karso/api/public_key/pem --output plop.txt -H "Authorization: Zota 1:U0sJM1m@-STSdfg4365fJOFUGbR4kFycBu1qGZPwf7gW6k2WWRBzTPUH7QutCgPw-SDss45_563sSDFdfg@dsf@456" --verbose //curl http://0.0.0.0:15080/karso/api/public_key/pem --output plop.txt -H "Authorization: Zota 1:U0sJM1m@-STSdfg4365fJOFUGbR4kFycBu1qGZPwf7gW6k2WWRBzTPUH7QutCgPw-SDss45_563sSDFdfg@dsf@456" --verbose
public KarsoAuthenticationFilter() {
super("karso");
}
@Override @Override
protected UserByToken validateToken(String authorization) throws Exception { protected UserByToken validateToken(String authorization) throws Exception {
if (authorization == null || authorization.length() < 25) { if (authorization == null || authorization.length() < 25) {

View File

@ -41,6 +41,10 @@ public class Application extends GenericTable{
@SQLComment("Expiration time ") @SQLComment("Expiration time ")
@SQLDefault("666") @SQLDefault("666")
public Integer ttl; public Integer ttl;
@SQLNotNull
@SQLComment("Right is manage with Karso")
@SQLDefault("0")
public Boolean manageRight;
public Application() { public Application() {
} }
@ -58,10 +62,3 @@ public class Application extends GenericTable{
'}'; '}';
} }
} }
/*
ALTER TABLE `application`
CHANGE `description` `description` varchar(2048) COLLATE 'utf8mb4_0900_ai_ci' NULL COMMENT 'description of the application' AFTER `name`,
CHANGE `redirect` `redirect` varchar(2048) COLLATE 'latin1_bin' NOT NULL COMMENT 'Token (can be not unique)' AFTER `description`,
CHANGE `redirectDev` `redirectDev` varchar(2048) COLLATE 'latin1_bin' NOT NULL DEFAULT 'http://localhost:4200/sso/' AFTER `redirect`,
CHANGE `notification` `notification` varchar(2048) COLLATE 'latin1_bin' NOT NULL DEFAULT 'http://localhost:4200/sso/notification' AFTER `redirectDev`;
*/

View File

@ -10,26 +10,20 @@ CREATE TABLE `application` (
*/ */
import org.kar.archidata.annotation.SQLIfNotExists;
import org.kar.archidata.annotation.SQLLimitSize;
import org.kar.archidata.annotation.SQLNotNull;
import org.kar.archidata.annotation.SQLTableName;
import com.fasterxml.jackson.annotation.JsonInclude;
@SQLTableName ("application")
@SQLIfNotExists
@JsonInclude(JsonInclude.Include.NON_NULL)
public class ApplicationSmall{ public class ApplicationSmall{
@SQLLimitSize(512)
public String name; public String name;
@SQLLimitSize(512)
public String description; public String description;
@SQLLimitSize(512)
@SQLNotNull
public String redirect; public String redirect;
public ApplicationSmall() { public ApplicationSmall() {
} }
public ApplicationSmall(String name, String description, String redirect) {
super();
this.name = name;
this.description = description;
this.redirect = redirect;
}
} }

View File

@ -0,0 +1,35 @@
package org.kar.karso.model;
import org.kar.archidata.annotation.SQLComment;
import org.kar.archidata.annotation.SQLForeignKey;
import org.kar.archidata.annotation.SQLIfNotExists;
import org.kar.archidata.annotation.SQLLimitSize;
import org.kar.archidata.annotation.SQLNotNull;
import org.kar.archidata.annotation.SQLTableName;
import org.kar.archidata.model.GenericTable;
import com.fasterxml.jackson.annotation.JsonInclude;
@SQLTableName ("right")
@SQLIfNotExists
@JsonInclude(JsonInclude.Include.NON_NULL)
public class Right extends GenericTable {
@SQLNotNull
@SQLComment("application-ID that have the reference of the right")
@SQLForeignKey("application")
public long applicationId;
@SQLNotNull
@SQLComment("user-ID ")
@SQLForeignKey("user")
public long userId;
@SQLNotNull
@SQLComment("rightDescription-ID of the right description")
@SQLForeignKey("rightDescription")
public long rightDescriptionId;
@SQLNotNull
@SQLLimitSize(1024)
@SQLComment("Value of the right")
public String value;
}

View File

@ -0,0 +1,39 @@
package org.kar.karso.model;
import org.kar.archidata.annotation.SQLComment;
import org.kar.archidata.annotation.SQLDefault;
import org.kar.archidata.annotation.SQLForeignKey;
import org.kar.archidata.annotation.SQLIfNotExists;
import org.kar.archidata.annotation.SQLLimitSize;
import org.kar.archidata.annotation.SQLNotNull;
import org.kar.archidata.annotation.SQLTableName;
import org.kar.archidata.model.GenericTable;
import com.fasterxml.jackson.annotation.JsonInclude;
@SQLTableName ("rightDescription")
@SQLIfNotExists
@JsonInclude(JsonInclude.Include.NON_NULL)
public class RightDescription extends GenericTable {
@SQLNotNull
@SQLComment("Application id that have the reference of the right")
@SQLForeignKey("application")
public long applicationId;
@SQLNotNull
@SQLLimitSize(64)
@SQLComment("Key of the property")
public String key;
@SQLNotNull
@SQLLimitSize(1024)
@SQLComment("Title of the right")
public String title;
@SQLNotNull
@SQLLimitSize(1024)
@SQLComment("Description of the right")
public String description;
@SQLNotNull
@SQLLimitSize(16)
@SQLComment("Type of the property")
@SQLDefault("\"BOOLEAN\"")
public String type = "BOOLEAN"; // this is a place-holder (current type supported BOOLEAN)
}

View File

@ -1,11 +1,14 @@
package org.kar.karso.model; package org.kar.karso.model;
import java.sql.Timestamp; import java.sql.Timestamp;
import java.util.List;
import org.kar.archidata.annotation.SQLComment;
import org.kar.archidata.annotation.SQLDefault; import org.kar.archidata.annotation.SQLDefault;
import org.kar.archidata.annotation.SQLIfNotExists; import org.kar.archidata.annotation.SQLIfNotExists;
import org.kar.archidata.annotation.SQLLimitSize; import org.kar.archidata.annotation.SQLLimitSize;
import org.kar.archidata.annotation.SQLNotNull; import org.kar.archidata.annotation.SQLNotNull;
import org.kar.archidata.annotation.SQLTableLinkGeneric;
import org.kar.archidata.annotation.SQLTableName; import org.kar.archidata.annotation.SQLTableName;
import org.kar.archidata.model.User; import org.kar.archidata.model.User;
@ -35,4 +38,8 @@ public class UserAuth extends User {
@SQLDefault("'0'") @SQLDefault("'0'")
@SQLNotNull @SQLNotNull
public boolean avatar = false; public boolean avatar = false;
@SQLComment("List of accessible application (if not set the application is not available)")
@SQLTableLinkGeneric
public List<Long> applications = null;
} }

View File

@ -0,0 +1,25 @@
package org.kar.karso.model;
/*
CREATE TABLE `application` (
`id` bigint NOT NULL COMMENT 'Unique ID of the application' AUTO_INCREMENT PRIMARY KEY,
`description` text COMMENT 'description of the application',
`token` varchar(128) COLLATE 'latin1_bin' NOT NULL COMMENT 'Token (can be not unique)'
) AUTO_INCREMENT=10;
*/
import org.kar.archidata.annotation.SQLIfNotExists;
import org.kar.archidata.annotation.SQLTableName;
import org.kar.archidata.model.GenericTable;
import com.fasterxml.jackson.annotation.JsonInclude;
@SQLTableName ("user_link_application")
@SQLIfNotExists
@JsonInclude(JsonInclude.Include.NON_NULL)
public class UserLinkApplication extends GenericTable{
public long user_id;
public long application_id;
}

View File

@ -1,22 +1,32 @@
package org.kar.karso.util; package org.kar.karso.util;
public class ConfigVariable { public class ConfigVariable {
public static final String BASE_NAME = "ORG_KARAUTH_"; public static String BASE_NAME = "ORG_KARAUTH_";
public static String frontFolder = System.getenv(BASE_NAME + "FRONT_FOLDER");
public static String expirationTime = System.getenv(BASE_NAME + "AUTH_EXPIRATION_TIME");
public static String uuid_for_key_generation = System.getenv(BASE_NAME + "UUID_KEY_ROOT");
public static String edge = System.getenv(BASE_NAME + "EDGE");
public static String getFrontFolder() { public static String getFrontFolder() {
String out = System.getenv(BASE_NAME + "FRONT_FOLDER"); if (frontFolder == null) {
if (out == null) {
return "/application/front"; return "/application/front";
} }
return out; return frontFolder;
}
public static String getUUIDKeyRoot() {
return uuid_for_key_generation;
} }
public static int getAuthExpirationTime() { public static int getAuthExpirationTime() {
String out = System.getenv(BASE_NAME + "AUTH_EXPIRATION_TIME"); String out = expirationTime;
if (out == null) { if (out == null) {
// default expiration is 33 days for the master Oauth token // default expiration is 33 days for the master Oauth token
return 60*24*33; return 60*24*33;
} }
return Integer.valueOf(out); return Integer.valueOf(out);
} }
public static Boolean getEdge() {
return Boolean.valueOf(edge);
}
} }

View File

@ -2,7 +2,6 @@
"$schema": "./node_modules/@angular/cli/lib/config/schema.json", "$schema": "./node_modules/@angular/cli/lib/config/schema.json",
"version": 1, "version": 1,
"newProjectRoot": "projects", "newProjectRoot": "projects",
"defaultProject": "karso",
"projects": { "projects": {
"karso": { "karso": {
"root": "", "root": "",
@ -14,10 +13,13 @@
"options": { "options": {
"outputPath": "dist", "outputPath": "dist",
"index": "src/index.html", "index": "src/index.html",
"main": "src/main.ts", "main": "src/app-root/main.ts",
"tsConfig": "src/tsconfig.app.json", "tsConfig": "src/tsconfig.app-root.json",
"polyfills": "src/polyfills.ts", "polyfills": "src/polyfills.ts",
"assets": ["src/assets", "src/favicon.ico"], "assets": [
"src/assets",
"src/favicon.ico"
],
"styles": [ "styles": [
"src/styles.less", "src/styles.less",
"src/generic_page.less", "src/generic_page.less",
@ -91,7 +93,10 @@
"src/theme.checkbox.less", "src/theme.checkbox.less",
"src/theme.modal.less" "src/theme.modal.less"
], ],
"assets": ["src/assets", "src/favicon.ico"] "assets": [
"src/assets",
"src/favicon.ico"
]
} }
}, },
"lint": { "lint": {
@ -99,14 +104,22 @@
"options": { "options": {
"fix": true, "fix": true,
"eslintConfig": ".eslintrc.js", "eslintConfig": ".eslintrc.js",
"lintFilePatterns": ["src/**/*.spec.ts", "src/**/*.ts"] "lintFilePatterns": [
"src/**/*.spec.ts",
"src/**/*.ts"
]
} }
}, },
"TTTTTTlint": { "TTTTTTlint": {
"builder": "@angular-devkit/build-angular:tslint", "builder": "@angular-devkit/build-angular:tslint",
"options": { "options": {
"tsConfig": ["src/tsconfig.app.json", "src/tsconfig.spec.json"], "tsConfig": [
"exclude": ["**/node_modules/**"] "src/tsconfig.app.json",
"src/tsconfig.spec.json"
],
"exclude": [
"**/node_modules/**"
]
} }
} }
} }
@ -126,8 +139,89 @@
"lint": { "lint": {
"builder": "@angular-devkit/build-angular:tslint", "builder": "@angular-devkit/build-angular:tslint",
"options": { "options": {
"tsConfig": ["e2e/tsconfig.e2e.json"], "tsConfig": [
"exclude": ["**/node_modules/**"] "e2e/tsconfig.e2e.json"
],
"exclude": [
"**/node_modules/**"
]
}
}
}
},
"karso-edge": {
"root": "",
"sourceRoot": "src",
"projectType": "application",
"architect": {
"build": {
"builder": "@angular-devkit/build-angular:browser",
"options": {
"outputPath": "dist",
"index": "src/index.html",
"main": "src/app-edge/main.ts",
"tsConfig": "src/tsconfig.app-edge.json",
"polyfills": "src/polyfills.ts",
"assets": [
"src/assets",
"src/favicon.ico"
],
"styles": [
"src/styles.less",
"src/generic_page.less",
"src/theme.color.blue.less",
"src/theme.checkbox.less",
"src/theme.modal.less"
],
"scripts": []
},
"configurations": {
"production": {
"optimization": true,
"outputHashing": "all",
"sourceMap": false,
"namedChunks": false,
"aot": true,
"extractLicenses": true,
"vendorChunk": false,
"buildOptimizer": true,
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.edge.prod.ts"
}
]
},
"develop": {
"optimization": false,
"outputHashing": "none",
"sourceMap": true,
"namedChunks": true,
"aot": true,
"extractLicenses": true,
"vendorChunk": true,
"buildOptimizer": false,
"fileReplacements": [
{
"replace": "src/environments/environment.ts",
"with": "src/environments/environment.edge.ts"
}
]
}
}
},
"serve": {
"builder": "@angular-devkit/build-angular:dev-server",
"options": {
"browserTarget": "karso:build"
},
"configurations": {
"production": {
"browserTarget": "karso-edge:build:production"
},
"develop": {
"browserTarget": "karso-edge:build:develop"
}
} }
} }
} }
@ -145,4 +239,4 @@
"cli": { "cli": {
"analytics": false "analytics": false
} }
} }

View File

@ -1,14 +1,15 @@
{ {
"name": "karideo", "name": "karso",
"version": "0.0.0", "version": "0.0.0",
"license": "MIT", "license": "MPL-2",
"scripts": { "scripts": {
"all": "npm run build && npm run test", "all": "npm run build && npm run test",
"ng": "ng", "ng": "ng",
"start": "ng serve --configuration=develop --watch --port 4200", "start": "ng serve karso --configuration=develop --watch --port 4200",
"build": "ng build --prod", "start_edge": "ng serve karso-edge --configuration=develop --watch --port 4199",
"test": "ng test", "build": "ng build karso --prod",
"test-coverage": "ng test --code-coverage", "test": "ng test karso",
"test-coverage": "ng test karso --code-coverage",
"lint": "ng lint", "lint": "ng lint",
"style": "prettier --write .", "style": "prettier --write .",
"e2e": "ng e2e" "e2e": "ng e2e"
@ -51,4 +52,4 @@
"karma-spec-reporter": "^0.0.36", "karma-spec-reporter": "^0.0.36",
"prettier": "^2.8.1" "prettier": "^2.8.1"
} }
} }

View File

@ -19,7 +19,7 @@ import {
ManageAccountsScene, ManageAccountsScene,
ApplicationsScene, ApplicationsScene,
ApplicationEditScene, ApplicationEditScene,
} from './scene'; } from '../base/scene';
import { OnlyAdminGuard, OnlyUnregisteredGuardHome, OnlyUsersGuard, OnlyUsersGuardHome } from 'common/service/session'; import { OnlyAdminGuard, OnlyUnregisteredGuardHome, OnlyUsersGuard, OnlyUsersGuardHome } from 'common/service/session';
import { ForbiddenScene, NotFound404Scene } from 'common/scene'; import { ForbiddenScene, NotFound404Scene } from 'common/scene';
@ -98,4 +98,4 @@ const routes: Routes = [
], ],
exports: [RouterModule], exports: [RouterModule],
}) })
export class AppRoutingModule {} export class AppRoutingModule { }

View File

@ -0,0 +1,161 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { Component, OnInit } from '@angular/core';
import { EventOnMenu } from 'common/component/top-menu/top-menu';
import { UserService } from 'common/service/user';
import { SessionService } from 'common/service/session';
import { MenuItem, MenuPosition } from 'common/model/menu-item';
import { SSOService } from 'common/service';
import { environment } from 'environments/environment';
enum MenuEventType {
SSO_SITE = 'SSO_SITE',
}
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.less'],
})
export class AppComponent implements OnInit {
title: string = environment.edgeMode ? 'Karso-edge' : 'Karso';
autoConnectedDone: boolean = false;
isConnected: boolean = false;
signUpEnable: boolean = true;
currentMenu: MenuItem[] = [];
constructor(
private userService: UserService,
private sessionService: SessionService,
private ssoService: SSOService
) { }
ngOnInit() {
console.log(`call with: ${window.location.href}`);
this.autoConnectedDone = false;
this.isConnected = false;
this.updateMainMenu();
const self = this;
this.sessionService.change.subscribe(isConnected => {
console.log(`receive event from session ...${isConnected}`);
self.isConnected = isConnected;
self.updateMainMenu();
});
this.userService
.checkAutoConnect()
.then(() => {
console.log(` ==>>>>> Auto-connect THEN !!!`);
self.autoConnectedDone = true;
})
.catch(error => {
console.log(` ==>>>>> Auto-connect CATCH !!! ${error}`);
self.autoConnectedDone = true;
})
.finally(() => {
console.log(` ==>>>>> Auto-connect FINALLY !!!`);
self.autoConnectedDone = true;
});
this.ssoService
.checkSignUpEnable()
.then((value: boolean) => {
console.log(`Get value signUp = ${value}`);
self.signUpEnable = value;
self.updateMainMenu();
})
.catch((error: any) => {
console.log(`Can not call the sso to check the sign-up_interface: ${error}`);
});
}
updateMainMenu(): void {
console.log('update main menu :');
if (this.isConnected) {
console.log(' ==> is connected');
this.currentMenu = [
{
position: MenuPosition.LEFT,
hover: `You are logged as: ${this.sessionService.getLogin()}`,
icon: 'menu',
title: 'Menu',
subMenu: [
{
position: MenuPosition.LEFT,
hover: 'Go to Home page',
icon: 'home',
title: 'Home',
navigateTo: 'home',
}, {
position: MenuPosition.LEFT,
hover: 'Exit connection',
icon: 'exit_to_app',
title: 'Sign out',
navigateTo: 'signout',
}
],
},
{
position: MenuPosition.RIGHT,
image: 'assets/images/avatar_generic.svg',
title: '',
subMenu: [
{
position: MenuPosition.LEFT,
hover: `You are logged as: <b>${this.sessionService.getLogin()}</b>`,
title: `Sign in as ${this.sessionService.getLogin()}`,
}, {
position: MenuPosition.LEFT,
hover: 'Exit connection',
icon: 'exit_to_app',
title: 'Sign out',
navigateTo: 'signout',
}, {
position: MenuPosition.RIGHT,
hover: 'Create a new account',
icon: 'eject',
title: 'Parent',
navigateTo: 'signup',
},
],
},
];
} else {
this.currentMenu = [
{
position: MenuPosition.LEFT,
hover: 'Go to Home page',
icon: 'home',
title: 'Home',
navigateTo: 'home',
},
{
position: MenuPosition.RIGHT,
hover: 'Create a new account',
icon: 'eject',
title: 'Parent',
callback: true,
otherData: MenuEventType.SSO_SITE,
},
{
position: MenuPosition.RIGHT,
hover: 'Login page',
icon: 'account_circle',
title: 'Sign-in',
navigateTo: 'signin',
},
];
}
console.log(' ==> DONE');
}
eventOnMenu(data: EventOnMenu): void {
switch (data.menu.otherData) {
case MenuEventType.SSO_SITE:
this.ssoService.requestOpenSite();
break;
}
}
}

View File

@ -25,7 +25,7 @@ import {
ManageAccountsScene, ManageAccountsScene,
ApplicationsScene, ApplicationsScene,
ApplicationEditScene, ApplicationEditScene,
} from 'app/scene'; } from 'base/scene';
import { import {
BddService, BddService,
CookiesService, CookiesService,
@ -44,7 +44,7 @@ import {
import { CommonModule } from '@angular/common'; import { CommonModule } from '@angular/common';
import { ErrorComponent, PopInComponent, SpinerComponent, TopMenuComponent, UploadFileComponent, PasswordEntryComponent, EntryComponent, AsyncActionStatusComponent, ErrorMessageStateComponent, CheckboxComponent, BurgerPropertyComponent, EntryValidatorComponent, RenderSettingsComponent, RenderFormComponent, EntryNumberComponent } from 'common/component'; import { ErrorComponent, PopInComponent, SpinerComponent, TopMenuComponent, UploadFileComponent, PasswordEntryComponent, EntryComponent, AsyncActionStatusComponent, ErrorMessageStateComponent, CheckboxComponent, BurgerPropertyComponent, EntryValidatorComponent, RenderSettingsComponent, RenderFormComponent, EntryNumberComponent } from 'common/component';
import { ForbiddenScene } from 'common/scene'; import { ForbiddenScene } from 'common/scene';
import { AdminUserService, ApplicationService, ApplicationTokenService, SettingsService } from 'app/service'; import { AdminUserService, ApplicationService, ApplicationTokenService, SettingsService } from 'base/service';
import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin'; import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin';
@NgModule({ @NgModule({
@ -133,4 +133,4 @@ import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin';
bootstrap: [AppComponent], bootstrap: [AppComponent],
schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA], schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA],
}) })
export class AppModule {} export class AppModule { }

View File

@ -1,8 +1,8 @@
import { enableProdMode } from '@angular/core'; import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic'; import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module'; import { AppModule } from './app.module';
import { environment } from './environments/environment'; import { environment } from '../environments/environment';
if (environment.production) { if (environment.production) {
enableProdMode(); enableProdMode();

View File

@ -0,0 +1,101 @@
/** @file
* @author Edouard DUPIN
* @copyright 2022, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router'; // CLI imports router
import {
ChangePasswordScene,
ForgotPasswordScene,
HelpScene,
HomeScene,
SettingsScene,
SignInScene,
SignOutScene,
SignUpScene,
HomeUnregisteredScene,
ManageAccountsScene,
ApplicationsScene,
ApplicationEditScene,
} from '../base/scene';
import { OnlyAdminGuard, OnlyUnregisteredGuardHome, OnlyUsersGuard, OnlyUsersGuardHome } from 'common/service/session';
import { ForbiddenScene, NotFound404Scene } from 'common/scene';
const routes: Routes = [
{ path: '', redirectTo: '/home', pathMatch: 'full' },
{ path: 'forbidden', component: ForbiddenScene },
// ------------------------------------
// -- home global interface
// ------------------------------------
{
path: 'home',
component: HomeScene,
canActivate: [OnlyUsersGuardHome], // this route to unregistered path when not logged ==> permit to simplify display
},
{
path: 'unregistered',
component: HomeUnregisteredScene,
canActivate: [OnlyUnregisteredGuardHome], // jump to the home when registered
},
{ path: 'forgot-password', component: ForgotPasswordScene },
{ path: 'help/:page', component: HelpScene },
{ path: 'help', component: HelpScene },
{ path: 'signin', component: SignInScene },
// SSO connection mode ==> redirect to the second part data package
{ path: 'signin/:applicationId/:dataReturn', component: SignInScene },
{ path: 'signin/:applicationId', component: SignInScene },
{ path: 'signup', component: SignUpScene },
{ path: 'signup/:applicationId/:dataReturn', component: SignUpScene },
{ path: 'signup/:applicationId', component: SignUpScene },
{ path: 'signout/:applicationId/:dataReturn', component: SignOutScene },
{ path: 'signout/:applicationId', component: SignOutScene },
{ path: 'signout', component: SignOutScene },
{
path: 'password',
component: ChangePasswordScene,
canActivate: [OnlyUsersGuard],
},
{
path: 'settings',
component: SettingsScene,
canActivate: [OnlyAdminGuard],
},
{
path: 'manage_accounts',
component: ManageAccountsScene,
canActivate: [OnlyAdminGuard],
},
{
path: 'applications',
component: ApplicationsScene,
canActivate: [OnlyAdminGuard],
},
{
path: 'application-edit/:applicationId',
component: ApplicationEditScene,
canActivate: [OnlyAdminGuard],
},
{
path: '**',
component: NotFound404Scene,
},
];
@NgModule({
imports: [
RouterModule.forRoot(routes, {
//enableTracing: true, // <-- debugging purposes only
}),
],
exports: [RouterModule],
})
export class AppRoutingModule { }

View File

@ -0,0 +1,6 @@
<!-- Generig global menu -->
<app-top-menu [menu]="currentMenu" (callback)="eventOnMenu($event)"></app-top-menu>
<!-- all interfaced pages -->
<div class="main-content">
<router-outlet *ngIf="autoConnectedDone"></router-outlet>
</div>

View File

@ -0,0 +1,44 @@
#create-exercice-button {
position: fixed;
display: block;
right: 0;
bottom: 0;
margin-right: 40px;
margin-bottom: 40px;
z-index: 900;
}
#save-exercice-button {
position: fixed;
display: block;
right: 0;
bottom: 0;
margin-right: 110px;
margin-bottom: 40px;
z-index: 900;
}
.main-content {
position: absolute;
//width: ~"calc(calc(100% / 5 ) * 5)";
width: 100%;
height: ~'calc(100% - 56px)';
top: 56px;
left: 0;
margin: 0;
padding: 0;
display: block;
position: fixed;
overflow-y: auto;
//background-color:#FF0;
/*
.main-reduce {
width: 40%;
height: 100%;
margin: 0;
padding: 0px 10% 0px 10%;
display: block;
overflow-y:scroll;
}
*/
}

View File

@ -7,9 +7,10 @@
import { Component, OnInit } from '@angular/core'; import { Component, OnInit } from '@angular/core';
import { EventOnMenu } from 'common/component/top-menu/top-menu'; import { EventOnMenu } from 'common/component/top-menu/top-menu';
import { UserService } from 'common/service/user'; import { UserService } from 'common/service/user';
import { SessionService } from 'common/service/session'; import { SessionService, UserRoles222 } from 'common/service/session';
import { MenuItem, MenuPosition } from 'common/model/menu-item'; import { MenuItem, MenuPosition } from 'common/model/menu-item';
import { SSOService } from 'common/service'; import { SSOService } from 'common/service';
import { environment } from 'environments/environment';
@Component({ @Component({
selector: 'app-root', selector: 'app-root',
@ -17,7 +18,7 @@ import { SSOService } from 'common/service';
styleUrls: ['./app.component.less'], styleUrls: ['./app.component.less'],
}) })
export class AppComponent implements OnInit { export class AppComponent implements OnInit {
title: string = 'Karideo'; title: string = environment.edgeMode ? 'Karso-edge' : 'Karso';
autoConnectedDone: boolean = false; autoConnectedDone: boolean = false;
isConnected: boolean = false; isConnected: boolean = false;
signUpEnable: boolean = true; signUpEnable: boolean = true;
@ -27,14 +28,14 @@ export class AppComponent implements OnInit {
private userService: UserService, private userService: UserService,
private sessionService: SessionService, private sessionService: SessionService,
private ssoService: SSOService private ssoService: SSOService
) {} ) { }
ngOnInit() { ngOnInit() {
console.log(`call with: ${window.location.href}`); console.log(`call with: ${window.location.href}`);
this.autoConnectedDone = false; this.autoConnectedDone = false;
this.isConnected = false; this.isConnected = false;
this.updateMainMenu(); this.updateMainMenu();
let self = this; const self = this;
this.sessionService.change.subscribe(isConnected => { this.sessionService.change.subscribe(isConnected => {
console.log(`receive event from session ...${isConnected}`); console.log(`receive event from session ...${isConnected}`);
self.isConnected = isConnected; self.isConnected = isConnected;
@ -43,15 +44,15 @@ export class AppComponent implements OnInit {
this.userService this.userService
.checkAutoConnect() .checkAutoConnect()
.then(() => { .then(() => {
console.log(` ==>>>>> Autoconnect THEN !!!`); console.log(` ==>>>>> Auto-connect THEN !!!`);
self.autoConnectedDone = true; self.autoConnectedDone = true;
}) })
.catch(error => { .catch(error => {
console.log(` ==>>>>> Autoconnect CATCH !!! ${error}`); console.log(` ==>>>>> Auto-connect CATCH !!! ${error}`);
self.autoConnectedDone = true; self.autoConnectedDone = true;
}) })
.finally(() => { .finally(() => {
console.log(` ==>>>>> Autoconnect FINALLY !!!`); console.log(` ==>>>>> Auto-connect FINALLY !!!`);
self.autoConnectedDone = true; self.autoConnectedDone = true;
}); });
this.ssoService this.ssoService
@ -65,7 +66,7 @@ export class AppComponent implements OnInit {
console.log(`Can not call the sso to check the sign-up_interface: ${error}`); console.log(`Can not call the sso to check the sign-up_interface: ${error}`);
}); });
} }
eventOnMenu(data: EventOnMenu): void {} eventOnMenu(data: EventOnMenu): void { }
updateMainMenu(): void { updateMainMenu(): void {
console.log('update main menu :'); console.log('update main menu :');
@ -104,28 +105,28 @@ export class AppComponent implements OnInit {
icon: 'settings', icon: 'settings',
title: 'Admin Settings', title: 'Admin Settings',
navigateTo: 'settings', navigateTo: 'settings',
enable: this.sessionService.userAdmin === true, enable: this.sessionService.hasRight(UserRoles222.admin),
}, { // TODO move this in the setting environment system ? }, { // TODO move this in the setting environment system ?
position: MenuPosition.LEFT, position: MenuPosition.LEFT,
hover: 'Admin of users', hover: 'Admin of users',
icon: 'manage_accounts', icon: 'manage_accounts',
title: 'Manage Accounts', title: 'Manage Accounts',
navigateTo: 'manage_accounts', navigateTo: 'manage_accounts',
enable: this.sessionService.userAdmin === true, enable: this.sessionService.hasRight(UserRoles222.admin),
},{ }, {
position: MenuPosition.LEFT, position: MenuPosition.LEFT,
hover: 'Admin of all the applications', hover: 'Admin of all the applications',
icon: 'app_registration', icon: 'app_registration',
title: 'Manage Applications', title: 'Manage Applications',
navigateTo: 'applications', navigateTo: 'applications',
enable: this.sessionService.userAdmin === true, enable: this.sessionService.hasRight(UserRoles222.admin),
}, },
], ],
}, },
{ {
position: MenuPosition.RIGHT, position: MenuPosition.RIGHT,
image: "assets/images/avatar_generic.svg", image: 'assets/images/avatar_generic.svg',
title: "", title: '',
subMenu: [ subMenu: [
{ {
position: MenuPosition.LEFT, position: MenuPosition.LEFT,
@ -138,13 +139,13 @@ export class AppComponent implements OnInit {
navigateTo: "settings", navigateTo: "settings",
}, */{ }, */{
position: MenuPosition.LEFT, position: MenuPosition.LEFT,
icon: "help", icon: 'help',
title: "Help", title: 'Help',
navigateTo: "help", navigateTo: 'help',
}, { }, {
position: MenuPosition.LEFT, position: MenuPosition.LEFT,
hover: "Exit connection", hover: 'Exit connection',
icon: "exit_to_app", icon: 'exit_to_app',
title: 'Sign out', title: 'Sign out',
navigateTo: 'signout', navigateTo: 'signout',
}, },

View File

@ -0,0 +1,137 @@
/** @file
* @author Edouard DUPIN
* @copyright 2018, Edouard DUPIN, all right reserved
* @license PROPRIETARY (see license file)
*/
import { BrowserModule } from '@angular/platform-browser';
import { NgModule, CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA } from '@angular/core';
import { RouterModule } from '@angular/router';
import { HttpClientModule } from '@angular/common/http';
import { FormsModule, ReactiveFormsModule } from '@angular/forms'; // this is needed for dynamic selection of the select
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import {
SignInScene,
SignUpScene,
ValidateEmailScene,
HomeScene,
ErrorViewerScene,
ForgotPasswordScene,
HelpScene,
SignOutScene,
ChangePasswordScene,
SettingsScene,
HomeUnregisteredScene,
ManageAccountsScene,
ApplicationsScene,
ApplicationEditScene,
} from 'base/scene';
import {
BddService,
CookiesService,
HttpWrapperService,
NotificationService,
OnlyAdminGuard,
OnlyUnregisteredGuardHome,
OnlyUsersGuard,
OnlyUsersGuardHome,
PopInService,
SessionService,
SSOService,
StorageService,
UserService,
} from 'common/service';
import { CommonModule } from '@angular/common';
import { ErrorComponent, PopInComponent, SpinerComponent, TopMenuComponent, UploadFileComponent, PasswordEntryComponent, EntryComponent, AsyncActionStatusComponent, ErrorMessageStateComponent, CheckboxComponent, BurgerPropertyComponent, EntryValidatorComponent, RenderSettingsComponent, RenderFormComponent, EntryNumberComponent } from 'common/component';
import { ForbiddenScene } from 'common/scene';
import { AdminUserService, ApplicationService, ApplicationTokenService, SettingsService } from 'base/service';
import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin';
import { environment } from 'environments/environment';
@NgModule({
declarations: [
AppComponent,
TopMenuComponent,
UploadFileComponent,
ErrorComponent,
PasswordEntryComponent,
EntryComponent,
EntryValidatorComponent,
SpinerComponent,
AsyncActionStatusComponent,
ErrorMessageStateComponent,
CheckboxComponent,
BurgerPropertyComponent,
RenderSettingsComponent,
RenderFormComponent,
EntryNumberComponent,
PopInComponent,
PopInUploadProgress,
PopInDeleteConfirm,
SignInScene,
SignUpScene,
SignOutScene,
ValidateEmailScene,
HomeScene,
ErrorViewerScene,
HelpScene,
ForgotPasswordScene,
SettingsScene,
ForbiddenScene,
ChangePasswordScene,
HomeUnregisteredScene,
ManageAccountsScene,
ApplicationsScene,
ApplicationEditScene
],
imports: [
BrowserModule,
RouterModule,
AppRoutingModule,
HttpClientModule,
FormsModule,
ReactiveFormsModule,
CommonModule,
],
// injectable element
providers: [
// application
AdminUserService,
ApplicationService,
ApplicationTokenService,
// common
BddService,
CookiesService,
HttpWrapperService,
StorageService,
PopInService,
SessionService,
UserService,
SSOService,
NotificationService,
SettingsService,
OnlyUsersGuard,
OnlyAdminGuard,
OnlyUsersGuardHome,
OnlyUnregisteredGuardHome,
],
exports: [
AppComponent,
TopMenuComponent,
PasswordEntryComponent,
UploadFileComponent,
ErrorComponent,
BurgerPropertyComponent,
BurgerPropertyComponent,
PopInComponent,
PopInUploadProgress,
PopInDeleteConfirm,
],
bootstrap: [AppComponent],
schemas: [CUSTOM_ELEMENTS_SCHEMA, NO_ERRORS_SCHEMA],
})
export class AppModule { }

View File

@ -0,0 +1,15 @@
import { enableProdMode } from '@angular/core';
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app.module';
import { environment } from '../environments/environment';
if (environment.production) {
enableProdMode();
}
platformBrowserDynamic()
.bootstrapModule(AppModule)
.catch(err => {
return console.log(err);
});

View File

@ -6,8 +6,8 @@
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, Input, OnInit } from '@angular/core'; import { ChangeDetectionStrategy, ChangeDetectorRef, Component, Input, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router'; import { ActivatedRoute } from '@angular/router';
import { ApplicationService, ApplicationModel, ApplicationTokenService } from 'app/service'; import { ApplicationService, ApplicationModel, ApplicationTokenService } from 'base/service';
import { ApplicationTokenModel } from 'app/service/application-token'; import { ApplicationTokenModel } from 'base/service/application-token';
import { AsyncActionState } from 'common/component'; import { AsyncActionState } from 'common/component';
import { CheckerParameterType, SettingsItem, SettingType } from 'common/component/render-settings/render-settings'; import { CheckerParameterType, SettingsItem, SettingType } from 'common/component/render-settings/render-settings';
import { NotificationService, PopInService } from 'common/service'; import { NotificationService, PopInService } from 'common/service';
@ -30,9 +30,9 @@ export class ApplicationEditScene implements OnInit {
private applicationTokenService: ApplicationTokenService, private applicationTokenService: ApplicationTokenService,
private activatedRoute: ActivatedRoute, private activatedRoute: ActivatedRoute,
private cdr: ChangeDetectorRef, private cdr: ChangeDetectorRef,
private popInService: PopInService, private popInService: PopInService,
private notificationService: NotificationService, private notificationService: NotificationService,
) { ) {
} }
ngOnInit() { ngOnInit() {
this.id = Number(this.activatedRoute.snapshot.paramMap.get('applicationId')); this.id = Number(this.activatedRoute.snapshot.paramMap.get('applicationId'));
@ -66,7 +66,7 @@ export class ApplicationEditScene implements OnInit {
} }
editApplicationMenu: SettingsItem[] = undefined; editApplicationMenu: SettingsItem[] = undefined;
// this permit to clear the input menu... // this permit to clear the input menu...
configureEditInput() { configureEditInput() {
this.editApplicationMenu = [ this.editApplicationMenu = [
@ -81,7 +81,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter application name', placeholder: 'Enter application name',
key: 'name', key: 'name',
value: this.application?.name, value: this.application?.name,
checker: (value) => { return this.checkName(value)}, checker: (value) => { return this.checkName(value) },
require: true, require: true,
}, },
{ {
@ -93,17 +93,17 @@ export class ApplicationEditScene implements OnInit {
{ {
type: SettingType.STRING, type: SettingType.STRING,
title: 'Redirect:', title: 'Redirect:',
description:"Redirect when login (http://):", description: "Redirect when login (http://):",
placeholder: 'Enter http redirect adresses', placeholder: 'Enter http redirect adresses',
key: 'redirect', key: 'redirect',
value: this.application?.redirect, value: this.application?.redirect,
checker: (value: CheckerParameterType) => { return this.checkRedirect(value)}, checker: (value: CheckerParameterType) => { return this.checkRedirect(value) },
require: true, require: true,
}, },
{ {
type: SettingType.STRING, type: SettingType.STRING,
title: 'Redirect (dev):', title: 'Redirect (dev):',
description:"Redirect development (http://):", description: "Redirect development (http://):",
placeholder: 'Enter http redirect adresses', placeholder: 'Enter http redirect adresses',
key: 'redirectDev', key: 'redirectDev',
value: this.application?.redirectDev, value: this.application?.redirectDev,
@ -111,8 +111,8 @@ export class ApplicationEditScene implements OnInit {
{ {
type: SettingType.STRING, type: SettingType.STRING,
title: 'Notification:', title: 'Notification:',
description:"Redirect development (http://):", description: "Redirect development (http://):",
placeholder:"http://xxx/sso-event", placeholder: "http://xxx/sso-event",
key: 'notification', key: 'notification',
value: this.application?.notification, value: this.application?.notification,
}, },
@ -123,7 +123,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: "888", placeholder: "888",
key: 'ttl', key: 'ttl',
value: this.application?.ttl, value: this.application?.ttl,
checker: (value: CheckerParameterType) => { return this.checkTTL(value)}, checker: (value: CheckerParameterType) => { return this.checkTTL(value) },
require: true, require: true,
}, },
]; ];
@ -165,7 +165,7 @@ export class ApplicationEditScene implements OnInit {
/** /**
* Request the creation of a new application. * Request the creation of a new application.
*/ */
onUpdateApplication(): void { onUpdateApplication(): void {
this.updateState = AsyncActionState.LOADING; this.updateState = AsyncActionState.LOADING;
let self = this; let self = this;
this.applicationService.update(this.id, this.dataUpdate) this.applicationService.update(this.id, this.dataUpdate)
@ -174,7 +174,7 @@ export class ApplicationEditScene implements OnInit {
self.updateState = AsyncActionState.DONE; self.updateState = AsyncActionState.DONE;
console.log(`Get new application data: ${JSON.stringify(data, null, 2)}`); console.log(`Get new application data: ${JSON.stringify(data, null, 2)}`);
self.application = data; self.application = data;
self.configureEditInput() self.configureEditInput()
setTimeout(() => { setTimeout(() => {
this.updateState = undefined; this.updateState = undefined;
}, 3000); }, 3000);
@ -231,7 +231,7 @@ export class ApplicationEditScene implements OnInit {
confirmDeleteApplicationToken: ApplicationTokenModel = undefined; confirmDeleteApplicationToken: ApplicationTokenModel = undefined;
deleteConfirmed() { deleteConfirmed() {
if(this.confirmDeleteApplicationToken !== undefined) { if (this.confirmDeleteApplicationToken !== undefined) {
this.removeApplicationConfirm(this.confirmDeleteApplicationToken); this.removeApplicationConfirm(this.confirmDeleteApplicationToken);
this.confirmDeleteComment = undefined; this.confirmDeleteComment = undefined;
this.confirmDeleteApplicationToken = undefined; this.confirmDeleteApplicationToken = undefined;
@ -240,7 +240,7 @@ export class ApplicationEditScene implements OnInit {
createTokenMenu: SettingsItem[] = [] createTokenMenu: SettingsItem[] = []
// this permit to clear the input menu... // this permit to clear the input menu...
configureInput() { configureInput() {
this.createTokenMenu = [ this.createTokenMenu = [
@ -250,7 +250,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter the token name / decription', placeholder: 'Enter the token name / decription',
key: 'name', key: 'name',
value: '', value: '',
checker: (value: CheckerParameterType) => { return this.checkName(value)}, checker: (value: CheckerParameterType) => { return this.checkName(value) },
require: true, require: true,
}, },
{ {
@ -259,7 +259,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter the Time To Lead (in day)', placeholder: 'Enter the Time To Lead (in day)',
key: 'ttl', key: 'ttl',
value: '', value: '',
checker: (value: CheckerParameterType) => { return this.checkTTL(value)}, checker: (value: CheckerParameterType) => { return this.checkTTL(value) },
require: true, require: true,
}, },
]; ];

View File

@ -4,6 +4,7 @@
<burger-property> <burger-property>
<name>Applications</name> <name>Applications</name>
<description>Availlable applications for this SSO</description> <description>Availlable applications for this SSO</description>
<body> <body>
<table class="table-model"> <table class="table-model">
<tr> <tr>
@ -23,16 +24,13 @@
<td>{{application.ttl}}</td> <td>{{application.ttl}}</td>
<td>{{application.notification}}</td> <td>{{application.notification}}</td>
<td> <td>
<button <button class="square-button login color-shadow-black"
class="square-button login color-shadow-black" (click)="onEditApplication($event, application)" type="submit">
(click)="onEditApplication($event, application)"
type="submit">
<i class="material-icons">edit</i> <i class="material-icons">edit</i>
</button>&nbsp; </button>&nbsp;
<button <button *ngIf="application.id !== 0"
class="square-button login color-button-cancel color-shadow-black" class="square-button login color-button-cancel color-shadow-black"
(click)="onRemoveApplication($event, application)" (click)="onRemoveApplication($event, application)" type="submit">
type="submit">
<i class="material-icons">delete_forever</i> <i class="material-icons">delete_forever</i>
</button> </button>
</td> </td>
@ -41,24 +39,19 @@
</body> </body>
</burger-property> </burger-property>
</div> </div>
<div class="clear"><br/></div> <div class="clear"><br /></div>
<div style="padding-top:15px;"> <div style="padding-top:15px;">
<burger-property> <burger-property>
<name>Create new application</name> <name>Create new application</name>
<description>Add a new application on the server</description> <description>Add a new application on the server</description>
<body> <body>
<app-render-form <app-render-form [values]="createApplicationMenu" (deltaValues)="onCreateValueDeltaValues($event)"
[values]="createApplicationMenu" (changeState)="onCreateValueState($event)"></app-render-form>
(deltaValues)="onCreateValueDeltaValues($event)"
(changeState)="onCreateValueState($event)"
></app-render-form>
</body> </body>
<footer> <footer>
<button <button class="button login color-button-validate color-shadow-black" id="create-button"
class="button login color-button-validate color-shadow-black" [disabled]="validateButtonCreateApplicationDisabled !== 0" (click)="onCreateApplication()"
id="create-button"
[disabled]="validateButtonCreateApplicationDisabled !== 0"
(click)="onCreateApplication()"
type="submit"> type="submit">
Create application Create application
</button> </button>
@ -68,6 +61,4 @@
<div class="clear"></div> <div class="clear"></div>
</div> </div>
<delete-confirm <delete-confirm [comment]="confirmDeleteComment" (callback)="deleteConfirmed()"></delete-confirm>
[comment]="confirmDeleteComment"
(callback)="deleteConfirmed()"></delete-confirm>

View File

@ -6,7 +6,7 @@
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core'; import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core';
import { Router } from '@angular/router'; import { Router } from '@angular/router';
import { ApplicationService, ApplicationModel } from 'app/service'; import { ApplicationService, ApplicationModel } from 'base/service';
import { AsyncActionState } from 'common/component'; import { AsyncActionState } from 'common/component';
import { CheckerParameterType, SettingsItem, SettingType } from 'common/component/render-settings/render-settings'; import { CheckerParameterType, SettingsItem, SettingType } from 'common/component/render-settings/render-settings';
import { NotificationService, PopInService } from 'common/service'; import { NotificationService, PopInService } from 'common/service';
@ -83,7 +83,7 @@ export class ApplicationsScene implements OnInit {
createApplicationMenu: SettingsItem[] = [] createApplicationMenu: SettingsItem[] = []
// this permit to clear the input menu... // this permit to clear the input menu...
configureInput() { configureInput() {
this.createApplicationMenu = [ this.createApplicationMenu = [
@ -93,7 +93,7 @@ export class ApplicationsScene implements OnInit {
placeholder: 'Enter application name', placeholder: 'Enter application name',
key: 'name', key: 'name',
value: '', value: '',
checker: (value) => { return this.checkName(value)}, checker: (value) => { return this.checkName(value) },
require: true, require: true,
}, },
{ {
@ -102,7 +102,7 @@ export class ApplicationsScene implements OnInit {
placeholder: 'Enter http redirect adresses', placeholder: 'Enter http redirect adresses',
key: 'redirect', key: 'redirect',
value: '', value: '',
checker: (value) => { return this.checkRedirect(value)}, checker: (value) => { return this.checkRedirect(value) },
require: true, require: true,
}, },
]; ];

View File

@ -7,7 +7,7 @@
import { Component, OnInit } from '@angular/core'; import { Component, OnInit } from '@angular/core';
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { createPasswordState } from 'common/utils'; import { createPasswordState } from 'common/utils';
import { AdminUserService } from 'app/service'; import { AdminUserService } from 'base/service';
export enum PasswordState { export enum PasswordState {
FILLING = "filling", FILLING = "filling",
@ -25,9 +25,9 @@ export class ChangePasswordScene {
/// State of the password scene... /// State of the password scene...
public updateState: PasswordState = PasswordState.FILLING; public updateState: PasswordState = PasswordState.FILLING;
/// status of the 3 fields: /// status of the 3 fields:
public passwordOldState: boolean|string = false; public passwordOldState: boolean | string = false;
public password1State: boolean|string = false; public password1State: boolean | string = false;
public password2State: boolean|string = false; public password2State: boolean | string = false;
/// data of the 3 field /// data of the 3 field
public passwordOld: string = ''; public passwordOld: string = '';
public password1: string = ''; public password1: string = '';
@ -35,12 +35,12 @@ export class ChangePasswordScene {
/// Validation button state /// Validation button state
public validateButtonDisabled: boolean = true; public validateButtonDisabled: boolean = true;
public error: string= ""; public error: string = "";
constructor( constructor(
private locate: Location, private locate: Location,
private adminUserService: AdminUserService private adminUserService: AdminUserService
) {} ) { }
/** /**
* update the state of the validation button. if all is OK, the button will became clickable * update the state of the validation button. if all is OK, the button will became clickable
*/ */
@ -100,13 +100,13 @@ export class ChangePasswordScene {
onChangePassword(): void { onChangePassword(): void {
this.updateState = PasswordState.SENDING; this.updateState = PasswordState.SENDING;
this.adminUserService.changePassword(this.passwordOld, this.password1) this.adminUserService.changePassword(this.passwordOld, this.password1)
.then(() => { .then(() => {
this.updateState = PasswordState.DONE; this.updateState = PasswordState.DONE;
}) })
.catch((error: any) => { .catch((error: any) => {
this.updateState = PasswordState.ERROR; this.updateState = PasswordState.ERROR;
this.error = error; this.error = error;
}); });
} }
/** /**
* Apply cancel on this page * Apply cancel on this page

View File

@ -8,7 +8,7 @@ import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router'; import { Router } from '@angular/router';
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { UserService } from 'common/service'; import { UserService } from 'common/service';
import { AdminUserService } from 'app/service'; import { AdminUserService } from 'base/service';
export function checkLoginValidity(value: string): boolean { export function checkLoginValidity(value: string): boolean {
let regexCheck = new RegExp('^[a-zA-Z0-9_\\.-]+$'); let regexCheck = new RegExp('^[a-zA-Z0-9_\\.-]+$');
@ -54,9 +54,9 @@ export class ForgotPasswordScene implements OnInit {
private locate: Location, private locate: Location,
private userService: UserService, private userService: UserService,
private adminUserService: AdminUserService private adminUserService: AdminUserService
) {} ) { }
ngOnInit() {} ngOnInit() { }
updateButtonVisibility(): void { updateButtonVisibility(): void {
if (this.loginOK === true && this.notARobot === true) { if (this.loginOK === true && this.notARobot === true) {

View File

@ -5,8 +5,8 @@
*/ */
import { Component, OnInit } from '@angular/core'; import { Component, OnInit } from '@angular/core';
import { ApplicationService } from 'app/service'; import { ApplicationService } from 'base/service';
import { GetApplicationSmallResponse, SpecificTokenResponse } from 'app/service/application'; import { GetApplicationSmallResponse, SpecificTokenResponse } from 'base/service/application';
import { UserService } from 'common/service'; import { UserService } from 'common/service';
@Component({ @Component({
@ -17,7 +17,7 @@ import { UserService } from 'common/service';
export class HomeScene implements OnInit { export class HomeScene implements OnInit {
error = ''; error = '';
dataList: GetApplicationSmallResponse[]; dataList: GetApplicationSmallResponse[];
constructor(private applicationService: ApplicationService, private userService: UserService) {} constructor(private applicationService: ApplicationService, private userService: UserService) { }
ngOnInit() { ngOnInit() {
let self = this; let self = this;

View File

@ -5,7 +5,7 @@
*/ */
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core'; import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core';
import { AdminUserService } from 'app/service'; import { AdminUserService } from 'base/service';
import { AsyncActionState } from 'common/component'; import { AsyncActionState } from 'common/component';
import { SessionService } from 'common/service'; import { SessionService } from 'common/service';
import { import {
@ -110,7 +110,7 @@ export class ManageAccountsScene implements OnInit {
private adminUserService: AdminUserService, private adminUserService: AdminUserService,
private sessionService: SessionService, private sessionService: SessionService,
private cdr: ChangeDetectorRef, private cdr: ChangeDetectorRef,
) { ) {
} }
ngOnInit() { ngOnInit() {
this.adminLogin = this.sessionService.getLogin(); this.adminLogin = this.sessionService.getLogin();
@ -141,7 +141,7 @@ export class ManageAccountsScene implements OnInit {
user.adminState = undefined; user.adminState = undefined;
self.cdr.detectChanges(); self.cdr.detectChanges();
}, 3000); }, 3000);
} }
).catch( ).catch(
(error: any) => { (error: any) => {
@ -155,7 +155,7 @@ export class ManageAccountsScene implements OnInit {
} }
); );
} }
onSetBlocked(value:boolean, user: any) { onSetBlocked(value: boolean, user: any) {
user.blocked = value; user.blocked = value;
console.log(`onSetBlocked: ${value} on ${user.login}`); console.log(`onSetBlocked: ${value} on ${user.login}`);
user.blockedState = AsyncActionState.LOADING; user.blockedState = AsyncActionState.LOADING;
@ -189,13 +189,13 @@ export class ManageAccountsScene implements OnInit {
public password: string = ''; public password: string = '';
public passwordState: boolean|string = false; public passwordState: boolean | string = false;
public login: string = ''; public login: string = '';
public loginState: boolean|string = false; public loginState: boolean | string = false;
public email: string = ''; public email: string = '';
public emailState: boolean|string = false; public emailState: boolean | string = false;
public validateButtonCreateUserDisabled: boolean = true; public validateButtonCreateUserDisabled: boolean = true;
/** /**
@ -254,7 +254,7 @@ export class ManageAccountsScene implements OnInit {
/** /**
* Check the login writing rules * Check the login writing rules
*/ */
checkLogin(newValue: string): void { checkLogin(newValue: string): void {
this.login = newValue; this.login = newValue;
this.loginState = createLoginState(this.login); this.loginState = createLoginState(this.login);
if (this.loginState === true) { if (this.loginState === true) {
@ -315,7 +315,7 @@ export class ManageAccountsScene implements OnInit {
self.emailState = 'ErrorOccured in fetching data ...'; self.emailState = 'ErrorOccured in fetching data ...';
self.updateButtonVisibility(); self.updateButtonVisibility();
} }
); );
this.updateButtonVisibility(); this.updateButtonVisibility();
} }
formatTimestamp(unix_timestamp: number): string { formatTimestamp(unix_timestamp: number): string {

View File

@ -6,7 +6,7 @@
import { ChangeDetectorRef, Component, OnInit } from '@angular/core'; import { ChangeDetectorRef, Component, OnInit } from '@angular/core';
import { ActivatedRoute } from '@angular/router'; import { ActivatedRoute } from '@angular/router';
import { SettingsService } from 'app/service'; import { SettingsService } from 'base/service';
import { isSettingsItem, SettingsItem, SettingType } from 'common/component/render-settings/render-settings'; import { isSettingsItem, SettingsItem, SettingType } from 'common/component/render-settings/render-settings';
import { import {
isNullOrUndefined, isNullOrUndefined,
@ -67,17 +67,17 @@ export class SettingsScene implements OnInit {
constructor( constructor(
private settingService: SettingsService, private settingService: SettingsService,
private cdr: ChangeDetectorRef, private cdr: ChangeDetectorRef,
) {} ) { }
menu: SettingsItem222[] = [ menu: SettingsItem222[] = [
{ {
title: 'Authentication:', title: 'Authentication:',
description: 'Manage the right of access to the web-services', description: 'Manage the right of access to the web-services',
values: undefined, values: undefined,
}, },
]; ];
// this permit to clear the input menu... // this permit to clear the input menu...
configureEditInput() { configureEditInput() {
const root = this.menu[0]; const root = this.menu[0];
root.values = [ root.values = [
@ -113,7 +113,7 @@ export class SettingsScene implements OnInit {
value: root.serverValues["EMAIL_VALIDATION_REQUIRED"], value: root.serverValues["EMAIL_VALIDATION_REQUIRED"],
}, },
], ],
this.menu[0].state = undefined; this.menu[0].state = undefined;
this.menu[0].newValues = {}; this.menu[0].newValues = {};
} }

View File

@ -9,8 +9,8 @@ import { ActivatedRoute, Router } from '@angular/router';
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { SessionService } from 'common/service'; import { SessionService } from 'common/service';
import { createLoginState, createPasswordState, getLoginType, isNullOrUndefined } from 'common/utils'; import { createLoginState, createPasswordState, getLoginType, isNullOrUndefined } from 'common/utils';
import { AdminUserService, ApplicationService } from 'app/service'; import { AdminUserService, ApplicationService } from 'base/service';
import { SpecificTokenResponse } from 'app/service/application'; import { SpecificTokenResponse } from 'base/service/application';
@Component({ @Component({
@ -19,10 +19,10 @@ import { SpecificTokenResponse } from 'app/service/application';
styleUrls: ['./sign-in.less'], styleUrls: ['./sign-in.less'],
}) })
export class SignInScene implements OnInit { export class SignInScene implements OnInit {
public loginState: boolean|string = false; public loginState: boolean | string = false;
public login: string = ''; public login: string = '';
public passwordState: boolean|string = false; public passwordState: boolean | string = false;
public password: string = ''; public password: string = '';
public loginButtonDisabled: boolean = true; public loginButtonDisabled: boolean = true;
@ -45,7 +45,7 @@ export class SignInScene implements OnInit {
private sessionService: SessionService, private sessionService: SessionService,
private applicationService: ApplicationService, private applicationService: ApplicationService,
private adminUserService: AdminUserService private adminUserService: AdminUserService
) {} ) { }
ngOnInit() { ngOnInit() {
const ssoApplicationId = this.route.snapshot.paramMap.get('applicationId'); const ssoApplicationId = this.route.snapshot.paramMap.get('applicationId');

View File

@ -9,8 +9,8 @@ import { ActivatedRoute, Router } from '@angular/router';
import { Location } from '@angular/common'; import { Location } from '@angular/common';
import { UserService } from 'common/service/user'; import { UserService } from 'common/service/user';
import { isNullOrUndefined } from 'common/utils'; import { isNullOrUndefined } from 'common/utils';
import { AdminUserService, ApplicationService } from 'app/service'; import { AdminUserService, ApplicationService } from 'base/service';
import { SpecificReturnResponse } from 'app/service/application'; import { SpecificReturnResponse } from 'base/service/application';
export function checkLoginValidity(value: string): boolean { export function checkLoginValidity(value: string): boolean {
let regexCheck = new RegExp('^[a-zA-Z0-9_\\.-]+$'); let regexCheck = new RegExp('^[a-zA-Z0-9_\\.-]+$');
@ -53,7 +53,7 @@ export class SignOutScene implements OnInit {
private userService: UserService, private userService: UserService,
private applicationService: ApplicationService, private applicationService: ApplicationService,
private adminUserService: AdminUserService private adminUserService: AdminUserService
) {} ) { }
ngOnInit() { ngOnInit() {
const ssoApplicationId = this.route.snapshot.paramMap.get('applicationId'); const ssoApplicationId = this.route.snapshot.paramMap.get('applicationId');

View File

@ -7,7 +7,7 @@
import { Component, OnInit } from '@angular/core'; import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router'; import { Router } from '@angular/router';
import { SSOService, UserService } from 'common/service'; import { SSOService, UserService } from 'common/service';
import { AdminUserService } from 'app/service'; import { AdminUserService } from 'base/service';
import { checkLoginValidity, checkEmailValidity, checkPasswordValidity } from '../forgot-password/forgot-password'; import { checkLoginValidity, checkEmailValidity, checkPasswordValidity } from '../forgot-password/forgot-password';
@Component({ @Component({

View File

@ -23,7 +23,7 @@ interface MessageLogIn {
time: string; time: string;
password: string; password: string;
} }
/*
interface MessageAnswer_USER_CONNECT { interface MessageAnswer_USER_CONNECT {
sessionId: string; sessionId: string;
login: string; login: string;
@ -31,6 +31,7 @@ interface MessageAnswer_USER_CONNECT {
role: string; role: string;
avatar: string; avatar: string;
} }
*/
@Injectable() @Injectable()
export class AdminUserService { export class AdminUserService {
@ -55,7 +56,7 @@ export class AdminUserService {
private loginSha(login: string, password: string, rememberMe?: boolean): Promise<boolean> { private loginSha(login: string, password: string, rememberMe?: boolean): Promise<boolean> {
// remove the current session interface // remove the current session interface
this.userService.removeSession(); this.userService.removeSession();
let self = this; const self = this;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
self.getTocken(login, password) self.getTocken(login, password)
.then((value: any) => { .then((value: any) => {
@ -82,7 +83,7 @@ export class AdminUserService {
// TODO: skip this part if the token is valid !!! // TODO: skip this part if the token is valid !!!
// this is here we need to route to the SSO on external system. // this is here we need to route to the SSO on external system.
let currentDate: string = new Date().toISOString(); const currentDate: string = new Date().toISOString();
let data: MessageLogIn; let data: MessageLogIn;
// create request: // create request:
if (this.identificationVersion === 1) { if (this.identificationVersion === 1) {
@ -139,7 +140,7 @@ export class AdminUserService {
setAdmin(userId: number, state: boolean): Promise<void> { setAdmin(userId: number, state: boolean): Promise<void> {
let body = state; const body = state;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.http this.http
.requestJson({ .requestJson({
@ -160,7 +161,7 @@ export class AdminUserService {
} }
setBlocked(userId: number, state: boolean): Promise<void> { setBlocked(userId: number, state: boolean): Promise<void> {
let body = state; const body = state;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.http this.http
.requestJson({ .requestJson({
@ -181,7 +182,7 @@ export class AdminUserService {
} }
createUsers(email: string, login: string, password: string): Promise<any> { createUsers(email: string, login: string, password: string): Promise<any> {
let body = { const body = {
email, email,
login, login,
password: sha512(password) password: sha512(password)
@ -210,7 +211,7 @@ export class AdminUserService {
return this.createSha(login, email, sha512(password)); return this.createSha(login, email, sha512(password));
} }
createSha(login: string, email: string, password: string) { createSha(login: string, email: string, password: string) {
let data = { const data = {
method: 'v?', method: 'v?',
login: login, login: login,
email: email, email: email,
@ -244,7 +245,7 @@ export class AdminUserService {
} }
checkLogin(login: string): Promise<boolean> { checkLogin(login: string): Promise<boolean> {
let params = { const params = {
login: login, login: login,
}; };
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
@ -274,7 +275,7 @@ export class AdminUserService {
} }
checkEMail(email: string): Promise<boolean> { checkEMail(email: string): Promise<boolean> {
let params = { const params = {
email: email, email: email,
}; };
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
@ -307,8 +308,8 @@ export class AdminUserService {
} }
changePassword(oldPassword: string, newPassword: string): Promise<void> { changePassword(oldPassword: string, newPassword: string): Promise<void> {
let time: string = new Date().toISOString(); const time: string = new Date().toISOString();
let login: string = this.sessionService.getLogin(); const login: string = this.sessionService.getLogin();
let method = null; let method = null;
let password = null; let password = null;
if (this.identificationVersion === 1) { if (this.identificationVersion === 1) {
@ -319,14 +320,14 @@ export class AdminUserService {
reject(`Internal Fail (contact administrator).`); reject(`Internal Fail (contact administrator).`);
}); });
} }
let body = { const body = {
method, method,
time, time,
login, login,
password, password,
newPassword: sha512(newPassword), newPassword: sha512(newPassword),
} };
let self = this; const self = this;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
self.http self.http
.request({ .request({

View File

@ -122,7 +122,6 @@ export class SettingsService {
for (let key of keys) { for (let key of keys) {
this.set(key, data[key]) this.set(key, data[key])
.then((result: boolean) => { .then((result: boolean) => {
multipleResponse.add(key, result); multipleResponse.add(key, result);
}) })
.catch((error: any) => { .catch((error: any) => {

View File

@ -6,98 +6,97 @@
import { Injectable, Output, EventEmitter } from '@angular/core'; import { Injectable, Output, EventEmitter } from '@angular/core';
import { CanActivate, Router } from '@angular/router'; import { CanActivate, Router } from '@angular/router';
import { isNullOrUndefined } from 'common/utils';
import { environment } from 'environments/environment';
export enum UserRoles222 { export enum UserRoles222 {
admin = 10000, admin = 'admin',
user = 1, user = 'user',
guest = 10, guest = 'guest',
} }
@Injectable() @Injectable()
export class SessionService { export class SessionService {
private tokenJwt = null; private tokenJwt = null;
public sessionId = null;
public userLogin = null; public userLogin = null;
public userAdmin = null;
public userEMail = null;
public userAvatar = null;
public userId = null; public userId = null;
public right: any = {};
@Output() change: EventEmitter<boolean> = new EventEmitter(); @Output() change: EventEmitter<boolean> = new EventEmitter();
constructor() {} constructor() { }
/** /**
* @brief Create a new session. * @brief Create a new session.
* *
* @param sessionId -
* @param userId - * @param userId -
* @param userLogin - * @param userLogin -
* @param userEMail - * @param tokenJwt -
* @param userAdmin -
* @param userAvatar -
*/ */
create({ create({
sessionId,
userId, userId,
userLogin, userLogin,
userEMail,
userAdmin,
userAvatar,
tokenJwt, tokenJwt,
}: { }: {
sessionId;
userId: string; userId: string;
userLogin: string; userLogin: string;
userEMail: string;
userAdmin: boolean;
userBlocked: boolean;
userRemoved: boolean;
userAvatar: string;
tokenJwt: string; tokenJwt: string;
}) { }) {
console.log( console.log(
`Session Create: userId=${userId} userLogin=${userLogin} userEMail=${userEMail} userAdmin=${userAdmin} userAvatar=${userAvatar} sessionId = ${sessionId} tokenJwt = ${tokenJwt}` `Session Create: userId=${userId} userLogin=${userLogin} tokenJwt = ${tokenJwt}`
); );
this.tokenJwt = tokenJwt; this.tokenJwt = tokenJwt;
this.sessionId = sessionId;
this.userId = userId; this.userId = userId;
this.userLogin = userLogin; this.userLogin = userLogin;
this.userAdmin = userAdmin; this.right = this.parseToken(tokenJwt);
this.userEMail = userEMail; console.log(`Retrieve right: ${JSON.stringify(this.right, null, 4)}`);
this.userAvatar = userAvatar;
this.change.emit(true); this.change.emit(true);
} }
b64_to_utf8(str: string): string {
return decodeURIComponent(window.atob(str));
}
parseToken(token: string): any {
const cut = token.split('.');
const decoded = this.b64_to_utf8(cut[1]);
const jsonModel = JSON.parse(decoded);
if (isNullOrUndefined(jsonModel.right)) {
return {};
}
if (isNullOrUndefined(jsonModel.right[environment.applName])) {
return {};
}
return jsonModel.right[environment.applName];
}
/** /**
* @brief destroy the current session. * @brief destroy the current session.
*/ */
destroy() { destroy() {
console.log('Session REMOVE'); console.log('Session REMOVE');
let last = this.sessionId;
this.sessionId = null;
this.tokenJwt = undefined; this.tokenJwt = undefined;
this.userId = null; this.userId = null;
this.userLogin = null; this.userLogin = null;
this.userAdmin = null; this.right = {};
this.userEMail = null;
this.userAvatar = null;
this.change.emit(false); this.change.emit(false);
} }
getToken(): string | undefined { getToken(): string | undefined {
return this.tokenJwt; return this.tokenJwt;
} }
islogged() { islogged() {
return this.sessionId !== null; return this.userId !== null;
} }
hasRight(type) { hasRight(type: UserRoles222): boolean {
if (type === UserRoles222.admin) { if (type === UserRoles222.admin) {
// sometime needed... if (isNullOrUndefined(this.right.ADMIN)) {
return this.userAdmin; return false;
}
return this.right.ADMIN;
} }
if (type === UserRoles222.user) { if (type === UserRoles222.user) {
// is connected ==> is user if (isNullOrUndefined(this.right.USER)) {
return this.sessionId !== null; return false;
}
return this.right.USER;
} }
if (type === UserRoles222.guest) { if (type === UserRoles222.guest) {
// all the other ... maybe unneeded // all the other ... maybe unneeded
@ -113,7 +112,7 @@ export class SessionService {
} }
getAvatar() { getAvatar() {
return 'assets/images/avatar_generic.svg'; return 'assets/images/avatar_generic.svg';
/* This is not ready : /* This is not ready:
if(this.userAvatar === false) { if(this.userAvatar === false) {
return 'assets/images/avatar_generic.svg'; return 'assets/images/avatar_generic.svg';
} }
@ -124,7 +123,7 @@ export class SessionService {
@Injectable() @Injectable()
export class OnlyUsersGuard implements CanActivate { export class OnlyUsersGuard implements CanActivate {
constructor(private sessionService: SessionService, private router: Router) {} constructor(private sessionService: SessionService, private router: Router) { }
canActivate() { canActivate() {
console.log('OnlyLoggedInUsers'); console.log('OnlyLoggedInUsers');
@ -139,7 +138,7 @@ export class OnlyUsersGuard implements CanActivate {
@Injectable() @Injectable()
export class OnlyUsersGuardHome implements CanActivate { export class OnlyUsersGuardHome implements CanActivate {
constructor(private sessionService: SessionService, private router: Router) {} constructor(private sessionService: SessionService, private router: Router) { }
canActivate() { canActivate() {
if (this.sessionService.hasRight(UserRoles222.user) || this.sessionService.hasRight(UserRoles222.admin)) { if (this.sessionService.hasRight(UserRoles222.user) || this.sessionService.hasRight(UserRoles222.admin)) {
@ -152,7 +151,7 @@ export class OnlyUsersGuardHome implements CanActivate {
} }
@Injectable() @Injectable()
export class OnlyUnregisteredGuardHome implements CanActivate { export class OnlyUnregisteredGuardHome implements CanActivate {
constructor(private sessionService: SessionService, private router: Router) {} constructor(private sessionService: SessionService, private router: Router) { }
canActivate() { canActivate() {
if (!this.sessionService.islogged()) { if (!this.sessionService.islogged()) {
@ -166,7 +165,7 @@ export class OnlyUnregisteredGuardHome implements CanActivate {
@Injectable() @Injectable()
export class OnlyAdminGuard implements CanActivate { export class OnlyAdminGuard implements CanActivate {
constructor(private sessionService: SessionService, private router: Router) {} constructor(private sessionService: SessionService, private router: Router) { }
canActivate() { canActivate() {
if (this.sessionService.hasRight(UserRoles222.user)) { if (this.sessionService.hasRight(UserRoles222.user)) {

View File

@ -44,7 +44,7 @@ export class SSOService {
) { ) {
return this.utf8_to_b64(data); return this.utf8_to_b64(data);
} }
let pathName = getApplicationLocation(); const pathName = getApplicationLocation();
if (isInArray(pathName, ['sso', '/sso', '/sso/'])) { if (isInArray(pathName, ['sso', '/sso', '/sso/'])) {
return this.utf8_to_b64('home'); return this.utf8_to_b64('home');
} }
@ -80,6 +80,12 @@ export class SSOService {
} }
return undefined; return undefined;
} }
/**
* Request Open SSO Global website
*/
requestOpenSite(): void {
window.location.href = environment.ssoSite;
}
/** /**
* Request SSO connection * Request SSO connection
*/ */

View File

@ -14,13 +14,13 @@ import { SessionService } from './session';
import { SSOService } from './sso'; import { SSOService } from './sso';
import { getApplicationLocation, isNullOrUndefined, sha512 } from 'common/utils'; import { getApplicationLocation, isNullOrUndefined, sha512 } from 'common/utils';
/*
interface MessageLogIn { interface MessageLogIn {
login: string; login: string;
method: string; method: string;
time: number; time: number;
password: string; password: string;
} }
interface MessageAnswer_USER_CONNECT { interface MessageAnswer_USER_CONNECT {
sessionId: string; sessionId: string;
login: string; login: string;
@ -28,7 +28,7 @@ interface MessageAnswer_USER_CONNECT {
role: string; role: string;
avatar: string; avatar: string;
} }
*/
@Injectable() @Injectable()
export class UserService { export class UserService {
// 0: Not hide password; 1 hide password; // 0: Not hide password; 1 hide password;
@ -69,9 +69,9 @@ export class UserService {
if (elems.length !== 3) { if (elems.length !== 3) {
return false; return false;
} }
//const tokenHeader = decodeURIComponent(window.atob( elems[0] )); // const tokenHeader = decodeURIComponent(window.atob( elems[0] ));
const tokenData = decodeURIComponent(window.atob(elems[1])); const tokenData = decodeURIComponent(window.atob(elems[1]));
//console.error(`Retreive local token: \nheader=${tokenHeader} \ndata=${tokenData}`); // console.error(`Retreive local token: \nheader=${tokenHeader} \ndata=${tokenData}`);
const parsedData = JSON.parse(tokenData); const parsedData = JSON.parse(tokenData);
console.debug( console.debug(
`Retreive token exp data=${new Date(parsedData.exp * 1000).toISOString()} < ${new Date().toISOString()}` `Retreive token exp data=${new Date(parsedData.exp * 1000).toISOString()} < ${new Date().toISOString()}`
@ -91,13 +91,13 @@ export class UserService {
*/ */
checkAutoConnect(): Promise<void> { checkAutoConnect(): Promise<void> {
let locationOrigin = getApplicationLocation(); let locationOrigin = getApplicationLocation();
let self = this; const self = this;
return new Promise<void>((resolve, reject) => { return new Promise<void>((resolve, reject) => {
// Need to use the windows global route to prevent the log in cycle ... // Need to use the windows global route to prevent the log in cycle ...
// And in the mlain application position, the route does not have curently root the page // And in the mlain application position, the route does not have curently root the page
let pathName = window.location.pathname; let pathName = window.location.pathname;
//console.log("start Path-name: '" + pathName + "'"); // console.log("start Path-name: '" + pathName + "'");
//console.log("check with: '" + environment.applName + "/sso/" + "'"); // console.log("check with: '" + environment.applName + "/sso/" + "'");
if (pathName.startsWith('/sso/') || pathName.startsWith(environment.applName + '/sso/')) { if (pathName.startsWith('/sso/') || pathName.startsWith(environment.applName + '/sso/')) {
console.log(' ==> SSo section'); console.log(' ==> SSo section');
reject(); reject();
@ -154,7 +154,7 @@ export class UserService {
} }
startSession(token: string, rememberMe: boolean): Promise<string> { startSession(token: string, rememberMe: boolean): Promise<string> {
let self = this; const self = this;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
self.retreiveMe(token) self.retreiveMe(token)
.then((value2: boolean) => { .then((value2: boolean) => {
@ -178,11 +178,11 @@ export class UserService {
} }
retreiveMe(token: string): Promise<boolean> { retreiveMe(token: string): Promise<boolean> {
console.log(`AuthService.loginWithToken ... '${token}'`); console.log(`AuthService.loginWithToken ... '${token}'`);
let self = this; const self = this;
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
this.http this.http
.requestJson({ .requestJson({
//server: 'karso', // server: 'karso',
endPoint: 'users/me', endPoint: 'users/me',
requestType: HTTPRequestModel.GET, requestType: HTTPRequestModel.GET,
accept: HTTPMimeType.JSON, accept: HTTPMimeType.JSON,
@ -193,14 +193,14 @@ export class UserService {
// TODO: check type ... // TODO: check type ...
console.log(`loginWithToken : get some data to check: ${JSON.stringify(response.data)}`); console.log(`loginWithToken : get some data to check: ${JSON.stringify(response.data)}`);
self.sessionService.create({ self.sessionService.create({
sessionId: response.data.sessionId, //sessionId: response.data.sessionId,
userId: response.data.id, userId: response.data.id,
userLogin: response.data.login, userLogin: response.data.login,
userEMail: response.data.email, //userEMail: response.data.email,
userAdmin: response.data.admin, //userAdmin: response.data.admin,
userBlocked: response.data.blocked, //userBlocked: response.data.blocked,
userRemoved: response.data.removed, //userRemoved: response.data.removed,
userAvatar: response.data.avatar, //userAvatar: response.data.avatar,
tokenJwt: token, tokenJwt: token,
}); });
resolve(true); resolve(true);
@ -258,8 +258,8 @@ export class UserService {
authorizedRoles = [_authorizedRoles]; authorizedRoles = [_authorizedRoles];
} }
return ( authService.isAuthenticated() return ( authService.isAuthenticated()
&& _authorizedRoles.indexOf(Session.userRole) !== -1 && _authorizedRoles.indexOf(Session.userRole) !== -1
); );
*/ */
return false; return false;
} }

View File

@ -0,0 +1,21 @@
// The file contents for the current environment will overwrite these during build.
// The build system defaults to the dev environment which uses `environment.ts`, but if you do
// `ng build --env=prod` then `environment.prod.ts` will be used instead.
// The list of which env maps to which file can be found in `.angular-cli.json`.
export const environment = {
production: true,
// URL of development API
applName: 'karso',
defaultServer: 'karso',
server: {
karso: `${location.origin}/karso/api`,
},
edgeMode: true,
// set to undefined sso* in case of internal authentication model
ssoSite: `${location.origin}/karso-edge`,
ssoSignIn: undefined,
ssoSignOut: undefined,
ssoSignUp: undefined,
tokenStoredInPermanentStorage: true,
};

View File

@ -0,0 +1,21 @@
// The file contents for the current environment will overwrite these during build.
// The build system defaults to the dev environment which uses `environment.ts`, but if you do
// `ng build --env=prod` then `environment.prod.ts` will be used instead.
// The list of which env maps to which file can be found in `.angular-cli.json`.
export const environment = {
production: false,
// URL of development API
applName: 'karso-edge',
defaultServer: 'karso',
server: {
karso: 'http://localhost:15080/karso-edge/api',
},
edgeMode: true,
// set to undefined sso* in case of internal authentication model
ssoSite: 'http://localhost:15080/karso',
ssoSignIn: undefined,
ssoSignOut: undefined,
ssoSignUp: undefined,
tokenStoredInPermanentStorage: true,
};

View File

@ -11,7 +11,9 @@ export const environment = {
server: { server: {
karso: `${location.origin}/karso/api`, karso: `${location.origin}/karso/api`,
}, },
// set to undefined sso* in case of internal authentification model edgeMode: false,
// set to undefined sso* in case of internal authentication model
ssoSite: undefined,
ssoSignIn: undefined, ssoSignIn: undefined,
ssoSignOut: undefined, ssoSignOut: undefined,
ssoSignUp: undefined, ssoSignUp: undefined,

View File

@ -11,7 +11,9 @@ export const environment = {
server: { server: {
karso: 'http://localhost:15080/karso/api', karso: 'http://localhost:15080/karso/api',
}, },
// set to undefined sso* in case of internal authentification model edgeMode: false,
// set to undefined sso* in case of internal authentication model
ssoSite: undefined,
ssoSignIn: undefined, ssoSignIn: undefined,
ssoSignOut: undefined, ssoSignOut: undefined,
ssoSignUp: undefined, ssoSignUp: undefined,

View File

@ -5,5 +5,9 @@
"baseUrl": "./", "baseUrl": "./",
"types": [] "types": []
}, },
"exclude": ["test.ts", "**/*.spec.ts"] "exclude": [
} "test.ts",
"**/*.spec.ts",
"app-root/**"
]
}

View File

@ -0,0 +1,13 @@
{
"extends": "../tsconfig.json",
"compilerOptions": {
"outDir": "../out-tsc/app",
"baseUrl": "./",
"types": []
},
"exclude": [
"test.ts",
"**/*.spec.ts",
"app-edge/**"
]
}

View File

@ -10,13 +10,28 @@
"emitDecoratorMetadata": true, "emitDecoratorMetadata": true,
"experimentalDecorators": true, "experimentalDecorators": true,
"target": "es2018", "target": "es2018",
"typeRoots": ["node_modules/@types"], "typeRoots": [
"lib": ["es2018", "dom"], "node_modules/@types"
],
"lib": [
"es2018",
"dom"
],
"module": "es2020", "module": "es2020",
"baseUrl": "./src/", "baseUrl": "./src/",
"paths": { "paths": {
"@app/*": ["./src/app/"], "@app-base/*": [
"@common/*": ["./src/common/"] "./src/base/"
],
"@app-root/*": [
"./src/app-root/"
],
"@app-edge/*": [
"./src/app-edge/"
],
"@common/*": [
"./src/common/"
]
} }
} }
} }

View File

@ -1,39 +1,66 @@
{ {
"rulesDirectory": ["node_modules/codelyzer"],
"rules": { "rules": {
"arrow-return-shorthand": true, "arrow-return-shorthand": true,
"callable-types": true, "callable-types": true,
"class-name": true, "class-name": true,
"comment-format": [true, "check-space"], "comment-format": [
true,
"check-space"
],
"curly": true, "curly": true,
"deprecation": { "deprecation": {
"severity": "warn" "severity": "warn"
}, },
"eofline": true, "eofline": true,
"forin": true, "forin": true,
"import-blacklist": [true, "rxjs/Rx"], "import-blacklist": [
true,
"rxjs/Rx"
],
"import-spacing": true, "import-spacing": true,
"indent": [true, "spaces"], "indent": [
true,
"tabs"
],
"interface-over-type-literal": true, "interface-over-type-literal": true,
"label-position": true, "label-position": true,
"max-line-length": [true, 140], "max-line-length": [
true,
140
],
"member-access": false, "member-access": false,
"member-ordering": [ "member-ordering": [
true, true,
{ {
"order": ["static-field", "instance-field", "static-method", "instance-method"] "order": [
"static-field",
"instance-field",
"static-method",
"instance-method"
]
} }
], ],
"no-arg": true, "no-arg": true,
"no-bitwise": true, "no-bitwise": true,
"no-console": [true, "debug", "info", "time", "timeEnd", "trace"], "no-console": [
true,
"debug",
"info",
"time",
"timeEnd",
"trace"
],
"no-construct": true, "no-construct": true,
"no-debugger": true, "no-debugger": true,
"no-duplicate-super": true, "no-duplicate-super": true,
"no-empty": false, "no-empty": false,
"no-empty-interface": true, "no-empty-interface": true,
"no-eval": true, "no-eval": true,
"no-inferrable-types": [true, "ignore-params"], "no-inferrable-types": [
true,
"ignore-params",
"ignore-properties"
],
"no-misused-new": true, "no-misused-new": true,
"no-non-null-assertion": true, "no-non-null-assertion": true,
"no-shadowed-variable": true, "no-shadowed-variable": true,
@ -45,12 +72,27 @@
"no-unused-expression": true, "no-unused-expression": true,
"no-var-keyword": true, "no-var-keyword": true,
"object-literal-sort-keys": false, "object-literal-sort-keys": false,
"one-line": [true, "check-open-brace", "check-catch", "check-else", "check-whitespace"], "one-line": [
true,
"check-open-brace",
"check-catch",
"check-else",
"check-whitespace"
],
"prefer-const": true, "prefer-const": true,
"quotemark": [true, "single"], "quotemark": [
true,
"single"
],
"radix": true, "radix": true,
"semicolon": [true, "always"], "semicolon": [
"triple-equals": [true, "allow-null-check"], true,
"always"
],
"triple-equals": [
true,
"allow-null-check"
],
"typedef-whitespace": [ "typedef-whitespace": [
true, true,
{ {
@ -63,9 +105,26 @@
], ],
"unified-signatures": true, "unified-signatures": true,
"variable-name": false, "variable-name": false,
"whitespace": [true, "check-branch", "check-decl", "check-operator", "check-separator", "check-type"], "whitespace": [
"directive-selector": [true, "attribute", "app", "camelCase"], true,
"component-selector": [true, "element", "app", "kebab-case"], "check-branch",
"check-decl",
"check-operator",
"check-separator",
"check-type"
],
"directive-selector": [
true,
"attribute",
"app",
"camelCase"
],
"component-selector": [
true,
"element",
"app",
"kebab-case"
],
"no-output-on-prefix": true, "no-output-on-prefix": true,
"no-inputs-metadata-property": true, "no-inputs-metadata-property": true,
"no-outputs-metadata-property": true, "no-outputs-metadata-property": true,
@ -77,4 +136,4 @@
"component-class-suffix": true, "component-class-suffix": true,
"directive-class-suffix": true "directive-class-suffix": true
} }
} }

View File

@ -24,7 +24,7 @@ CREATE USER 'karso'@'%' IDENTIFIED BY 'base_db_password';
GRANT ALL PRIVILEGES ON `karso`.* TO 'karso'@'%'; GRANT ALL PRIVILEGES ON `karso`.* TO 'karso'@'%';
FLUSH PRIVILEGES; FLUSH PRIVILEGES;
``` ```
> **_Note_** the base_db_password with the production password. this one is for development environment > **_Note_** the `base_db_password` with the production password. this one is for development environment
To start the service To start the service