[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>
<groupId>kangaroo-and-rabbit</groupId>
<artifactId>archidata</artifactId>
<version>0.3.2</version>
<version>0.3.5</version>
</dependency>
<!-- testing -->
<dependency>

View File

@ -12,8 +12,11 @@ import org.kar.karso.api.UserResource;
import org.kar.karso.filter.KarsoAuthenticationFilter;
import org.kar.karso.model.Application;
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.UserAuth;
import org.kar.karso.util.ConfigVariable;
//import org.kar.archidata.model.Migration;
import org.kar.archidata.SqlWrapper;
import org.kar.archidata.catcher.ExceptionCatcher;
@ -38,10 +41,11 @@ public class WebLauncher {
}
public static void main(String[] args) throws InterruptedException {
ConfigBaseVariable.bdDatabase = "karso";
ConfigBaseVariable.bdDatabase =
"karso";
try {
JWTWrapper.initLocalToken();
JWTWrapper.initLocalToken(ConfigVariable.getUUIDKeyRoot());
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
@ -57,17 +61,33 @@ public class WebLauncher {
out += SqlWrapper.createTable(UserAuth.class);
out += SqlWrapper.createTable(Application.class);
out += SqlWrapper.createTable(ApplicationToken.class);
out += SqlWrapper.createTable(RightDescription.class);
out += SqlWrapper.createTable(Right.class);
// default admin: "karadmin" password: "adminA@666"
out += """
INSERT INTO `user` (`login`, `password`, `email`, `admin`) VALUES
('karadmin', '0ddcac5ede3f1300a1ce5948ab15112f2810130531d578ab8bc4dc131652d7cf7a3ff6e827eb957bff43bc2c65a6a1d46722e5b3a2343ac3176a33ea7250080b',
INSERT INTO `application` (`id`, `name`, `description`, `redirect`, `redirectDev`, `notification`, `ttl`) VALUES
('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);
""";
out += """
INSERT INTO `settings` (`key`, `right`, `type`, `value`) VALUES
('SIGN_UP_ENABLE', 'rwr-r-', 'BOOLEAN', 'false'),
('SIGN_IN_ENABLE', 'rwr-r-', 'BOOLEAN', 'true'),
('SIGN_UP_FILTER', 'rw----', 'STRING', '.*'),
('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);
System.out.println(out);
@ -123,7 +143,6 @@ public class WebLauncher {
try {
server.start();
System.out.println("Jersey app started at " + getBaseURI());
System.out.println("Press CTRL^C to exit..");
Thread.currentThread().join();
} catch (Exception e) {
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;
import org.kar.archidata.SqlWrapper;
import org.kar.archidata.WhereCondition;
import org.kar.archidata.filter.GenericContext;
import org.kar.karso.model.*;
import org.kar.archidata.util.JWTWrapper;
import org.kar.archidata.annotation.security.RolesAllowed;
import org.kar.archidata.exception.InputException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import jakarta.ws.rs.*;
import jakarta.ws.rs.core.Context;
@ -22,28 +26,67 @@ public class 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
@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");
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
@Path("small")
@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");
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
@Path("get_token")
@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();
System.out.println("== USER ? " + gc.user);
System.out.println("== USER ? " + gc.userByToken);
if (application == null) {
String result = "Input error missing parameter: 'application'";
@ -60,7 +103,7 @@ public class ApplicationResource {
Application appl = null;
try {
appl = SqlWrapper.getWhere(Application.class, "name", "=", applicationName);
appl = SqlWrapper.getWhere(Application.class, List.of(new WhereCondition("name", "=", applicationName)), false);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
@ -72,11 +115,64 @@ public class ApplicationResource {
if (appl == null) {
String result = "Authentiocate-wrong email/login '" + applicationName + "')";
System.out.println(" result: " + result);
return Response.status(404).entity(result).build();
return Response.status(401).entity(result).build();
}
// Manage application right here...
String ret = JWTWrapper.generateJWToken(gc.user.id, gc.user.login, "KarAuth", applicationName, appl.ttl);
if (false) {
// the pplication id is not streamed in the application liny in the where elements
// 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);
String returnAdress = appl.redirect;
if (isDev) {
@ -93,7 +189,7 @@ public class ApplicationResource {
System.out.println("Get log_out()");
System.out.println("=====================================");
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user);
System.out.println("== USER ? " + gc.userByToken);
if (application == null) {
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");
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"));
return Response.status(201).entity("{ \"value\":\"" + res.value + "\"}").build();
}

View File

@ -1,7 +1,6 @@
package org.kar.karso.api;
import org.kar.archidata.model.GetToken;
import org.kar.archidata.model.User;
import org.kar.archidata.SqlWrapper;
import org.kar.archidata.WhereCondition;
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.karso.model.*;
import org.kar.karso.util.ConfigVariable;
import com.fasterxml.jackson.annotation.JsonInclude;
import org.kar.archidata.util.JWTWrapper;
import jakarta.ws.rs.*;
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.SecurityContext;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
@ -31,6 +35,18 @@ import java.time.LocalDateTime;
@Produces( MediaType.APPLICATION_JSON)
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() {
}
@GET
@ -47,6 +63,23 @@ public class UserResource {
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
@Path("{id}/set_admin")
@RolesAllowed("ADMIN")
@ -128,11 +161,11 @@ public class UserResource {
@GET
@Path("me")
@RolesAllowed("USER")
public User getMe(@Context SecurityContext sc) {
public UserOut getMe(@Context SecurityContext sc) {
System.out.println("getMe()");
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user);
return gc.user;
System.out.println("== USER ? " + gc.userByToken);
return new UserOut(gc.userByToken.id, gc.userByToken.name);
}
@POST
@ -141,7 +174,7 @@ public class UserResource {
public Response changePassword(@Context SecurityContext sc, ChangePassword data) throws Exception {
System.out.println("ChangePassword()");
GenericContext gc = (GenericContext) sc.getUserPrincipal();
System.out.println("== USER ? " + gc.user);
System.out.println("== USER ? " + gc.userByToken);
if(data == null) {
throw new InputException("data", "No data set...");
@ -250,8 +283,22 @@ public class UserResource {
@Consumes(MediaType.APPLICATION_JSON)
public GetToken getToken(DataGetToken data) throws Exception {
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();
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:
UserAuth newUser = new UserAuth();

View File

@ -21,6 +21,10 @@ 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
public KarsoAuthenticationFilter() {
super("karso");
}
@Override
protected UserByToken validateToken(String authorization) throws Exception {
if (authorization == null || authorization.length() < 25) {

View File

@ -41,6 +41,10 @@ public class Application extends GenericTable{
@SQLComment("Expiration time ")
@SQLDefault("666")
public Integer ttl;
@SQLNotNull
@SQLComment("Right is manage with Karso")
@SQLDefault("0")
public Boolean manageRight;
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{
@SQLLimitSize(512)
public String name;
@SQLLimitSize(512)
public String description;
@SQLLimitSize(512)
@SQLNotNull
public String redirect;
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;
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.SQLIfNotExists;
import org.kar.archidata.annotation.SQLLimitSize;
import org.kar.archidata.annotation.SQLNotNull;
import org.kar.archidata.annotation.SQLTableLinkGeneric;
import org.kar.archidata.annotation.SQLTableName;
import org.kar.archidata.model.User;
@ -35,4 +38,8 @@ public class UserAuth extends User {
@SQLDefault("'0'")
@SQLNotNull
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;
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() {
String out = System.getenv(BASE_NAME + "FRONT_FOLDER");
if (out == null) {
if (frontFolder == null) {
return "/application/front";
}
return out;
return frontFolder;
}
public static String getUUIDKeyRoot() {
return uuid_for_key_generation;
}
public static int getAuthExpirationTime() {
String out = System.getenv(BASE_NAME + "AUTH_EXPIRATION_TIME");
String out = expirationTime;
if (out == null) {
// default expiration is 33 days for the master Oauth token
return 60*24*33;
}
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",
"version": 1,
"newProjectRoot": "projects",
"defaultProject": "karso",
"projects": {
"karso": {
"root": "",
@ -14,10 +13,13 @@
"options": {
"outputPath": "dist",
"index": "src/index.html",
"main": "src/main.ts",
"tsConfig": "src/tsconfig.app.json",
"main": "src/app-root/main.ts",
"tsConfig": "src/tsconfig.app-root.json",
"polyfills": "src/polyfills.ts",
"assets": ["src/assets", "src/favicon.ico"],
"assets": [
"src/assets",
"src/favicon.ico"
],
"styles": [
"src/styles.less",
"src/generic_page.less",
@ -91,7 +93,10 @@
"src/theme.checkbox.less",
"src/theme.modal.less"
],
"assets": ["src/assets", "src/favicon.ico"]
"assets": [
"src/assets",
"src/favicon.ico"
]
}
},
"lint": {
@ -99,14 +104,22 @@
"options": {
"fix": true,
"eslintConfig": ".eslintrc.js",
"lintFilePatterns": ["src/**/*.spec.ts", "src/**/*.ts"]
"lintFilePatterns": [
"src/**/*.spec.ts",
"src/**/*.ts"
]
}
},
"TTTTTTlint": {
"builder": "@angular-devkit/build-angular:tslint",
"options": {
"tsConfig": ["src/tsconfig.app.json", "src/tsconfig.spec.json"],
"exclude": ["**/node_modules/**"]
"tsConfig": [
"src/tsconfig.app.json",
"src/tsconfig.spec.json"
],
"exclude": [
"**/node_modules/**"
]
}
}
}
@ -126,8 +139,89 @@
"lint": {
"builder": "@angular-devkit/build-angular:tslint",
"options": {
"tsConfig": ["e2e/tsconfig.e2e.json"],
"exclude": ["**/node_modules/**"]
"tsConfig": [
"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"
}
}
}
}

View File

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

View File

@ -19,7 +19,7 @@ import {
ManageAccountsScene,
ApplicationsScene,
ApplicationEditScene,
} from './scene';
} from '../base/scene';
import { OnlyAdminGuard, OnlyUnregisteredGuardHome, OnlyUsersGuard, OnlyUsersGuardHome } from 'common/service/session';
import { ForbiddenScene, NotFound404Scene } from 'common/scene';
@ -98,4 +98,4 @@ const routes: Routes = [
],
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,
ApplicationsScene,
ApplicationEditScene,
} from 'app/scene';
} from 'base/scene';
import {
BddService,
CookiesService,
@ -44,7 +44,7 @@ import {
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 'app/service';
import { AdminUserService, ApplicationService, ApplicationTokenService, SettingsService } from 'base/service';
import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin';
@NgModule({
@ -133,4 +133,4 @@ import { PopInUploadProgress, PopInDeleteConfirm } from 'common/popin';
bootstrap: [AppComponent],
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 { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
import { AppModule } from './app/app.module';
import { environment } from './environments/environment';
import { AppModule } from './app.module';
import { environment } from '../environments/environment';
if (environment.production) {
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 { EventOnMenu } from 'common/component/top-menu/top-menu';
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 { SSOService } from 'common/service';
import { environment } from 'environments/environment';
@Component({
selector: 'app-root',
@ -17,7 +18,7 @@ import { SSOService } from 'common/service';
styleUrls: ['./app.component.less'],
})
export class AppComponent implements OnInit {
title: string = 'Karideo';
title: string = environment.edgeMode ? 'Karso-edge' : 'Karso';
autoConnectedDone: boolean = false;
isConnected: boolean = false;
signUpEnable: boolean = true;
@ -27,14 +28,14 @@ export class AppComponent implements OnInit {
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();
let self = this;
const self = this;
this.sessionService.change.subscribe(isConnected => {
console.log(`receive event from session ...${isConnected}`);
self.isConnected = isConnected;
@ -43,15 +44,15 @@ export class AppComponent implements OnInit {
this.userService
.checkAutoConnect()
.then(() => {
console.log(` ==>>>>> Autoconnect THEN !!!`);
console.log(` ==>>>>> Auto-connect THEN !!!`);
self.autoConnectedDone = true;
})
.catch(error => {
console.log(` ==>>>>> Autoconnect CATCH !!! ${error}`);
console.log(` ==>>>>> Auto-connect CATCH !!! ${error}`);
self.autoConnectedDone = true;
})
.finally(() => {
console.log(` ==>>>>> Autoconnect FINALLY !!!`);
console.log(` ==>>>>> Auto-connect FINALLY !!!`);
self.autoConnectedDone = true;
});
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}`);
});
}
eventOnMenu(data: EventOnMenu): void {}
eventOnMenu(data: EventOnMenu): void { }
updateMainMenu(): void {
console.log('update main menu :');
@ -104,28 +105,28 @@ export class AppComponent implements OnInit {
icon: 'settings',
title: 'Admin Settings',
navigateTo: 'settings',
enable: this.sessionService.userAdmin === true,
enable: this.sessionService.hasRight(UserRoles222.admin),
}, { // TODO move this in the setting environment system ?
position: MenuPosition.LEFT,
hover: 'Admin of users',
icon: 'manage_accounts',
title: 'Manage Accounts',
navigateTo: 'manage_accounts',
enable: this.sessionService.userAdmin === true,
},{
enable: this.sessionService.hasRight(UserRoles222.admin),
}, {
position: MenuPosition.LEFT,
hover: 'Admin of all the applications',
icon: 'app_registration',
title: 'Manage Applications',
navigateTo: 'applications',
enable: this.sessionService.userAdmin === true,
enable: this.sessionService.hasRight(UserRoles222.admin),
},
],
},
{
position: MenuPosition.RIGHT,
image: "assets/images/avatar_generic.svg",
title: "",
image: 'assets/images/avatar_generic.svg',
title: '',
subMenu: [
{
position: MenuPosition.LEFT,
@ -138,13 +139,13 @@ export class AppComponent implements OnInit {
navigateTo: "settings",
}, */{
position: MenuPosition.LEFT,
icon: "help",
title: "Help",
navigateTo: "help",
icon: 'help',
title: 'Help',
navigateTo: 'help',
}, {
position: MenuPosition.LEFT,
hover: "Exit connection",
icon: "exit_to_app",
hover: 'Exit connection',
icon: 'exit_to_app',
title: 'Sign out',
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 { ActivatedRoute } from '@angular/router';
import { ApplicationService, ApplicationModel, ApplicationTokenService } from 'app/service';
import { ApplicationTokenModel } from 'app/service/application-token';
import { ApplicationService, ApplicationModel, ApplicationTokenService } from 'base/service';
import { ApplicationTokenModel } from 'base/service/application-token';
import { AsyncActionState } from 'common/component';
import { CheckerParameterType, SettingsItem, SettingType } from 'common/component/render-settings/render-settings';
import { NotificationService, PopInService } from 'common/service';
@ -81,7 +81,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter application name',
key: 'name',
value: this.application?.name,
checker: (value) => { return this.checkName(value)},
checker: (value) => { return this.checkName(value) },
require: true,
},
{
@ -93,17 +93,17 @@ export class ApplicationEditScene implements OnInit {
{
type: SettingType.STRING,
title: 'Redirect:',
description:"Redirect when login (http://):",
description: "Redirect when login (http://):",
placeholder: 'Enter http redirect adresses',
key: 'redirect',
value: this.application?.redirect,
checker: (value: CheckerParameterType) => { return this.checkRedirect(value)},
checker: (value: CheckerParameterType) => { return this.checkRedirect(value) },
require: true,
},
{
type: SettingType.STRING,
title: 'Redirect (dev):',
description:"Redirect development (http://):",
description: "Redirect development (http://):",
placeholder: 'Enter http redirect adresses',
key: 'redirectDev',
value: this.application?.redirectDev,
@ -111,8 +111,8 @@ export class ApplicationEditScene implements OnInit {
{
type: SettingType.STRING,
title: 'Notification:',
description:"Redirect development (http://):",
placeholder:"http://xxx/sso-event",
description: "Redirect development (http://):",
placeholder: "http://xxx/sso-event",
key: 'notification',
value: this.application?.notification,
},
@ -123,7 +123,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: "888",
key: 'ttl',
value: this.application?.ttl,
checker: (value: CheckerParameterType) => { return this.checkTTL(value)},
checker: (value: CheckerParameterType) => { return this.checkTTL(value) },
require: true,
},
];
@ -231,7 +231,7 @@ export class ApplicationEditScene implements OnInit {
confirmDeleteApplicationToken: ApplicationTokenModel = undefined;
deleteConfirmed() {
if(this.confirmDeleteApplicationToken !== undefined) {
if (this.confirmDeleteApplicationToken !== undefined) {
this.removeApplicationConfirm(this.confirmDeleteApplicationToken);
this.confirmDeleteComment = undefined;
this.confirmDeleteApplicationToken = undefined;
@ -250,7 +250,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter the token name / decription',
key: 'name',
value: '',
checker: (value: CheckerParameterType) => { return this.checkName(value)},
checker: (value: CheckerParameterType) => { return this.checkName(value) },
require: true,
},
{
@ -259,7 +259,7 @@ export class ApplicationEditScene implements OnInit {
placeholder: 'Enter the Time To Lead (in day)',
key: 'ttl',
value: '',
checker: (value: CheckerParameterType) => { return this.checkTTL(value)},
checker: (value: CheckerParameterType) => { return this.checkTTL(value) },
require: true,
},
];

View File

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

View File

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

View File

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

View File

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

View File

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

View File

@ -5,7 +5,7 @@
*/
import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnInit } from '@angular/core';
import { AdminUserService } from 'app/service';
import { AdminUserService } from 'base/service';
import { AsyncActionState } from 'common/component';
import { SessionService } from 'common/service';
import {
@ -155,7 +155,7 @@ export class ManageAccountsScene implements OnInit {
}
);
}
onSetBlocked(value:boolean, user: any) {
onSetBlocked(value: boolean, user: any) {
user.blocked = value;
console.log(`onSetBlocked: ${value} on ${user.login}`);
user.blockedState = AsyncActionState.LOADING;
@ -189,13 +189,13 @@ export class ManageAccountsScene implements OnInit {
public password: string = '';
public passwordState: boolean|string = false;
public passwordState: boolean | string = false;
public login: string = '';
public loginState: boolean|string = false;
public loginState: boolean | string = false;
public email: string = '';
public emailState: boolean|string = false;
public emailState: boolean | string = false;
public validateButtonCreateUserDisabled: boolean = true;
/**

View File

@ -6,7 +6,7 @@
import { ChangeDetectorRef, Component, OnInit } from '@angular/core';
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 {
isNullOrUndefined,
@ -67,7 +67,7 @@ export class SettingsScene implements OnInit {
constructor(
private settingService: SettingsService,
private cdr: ChangeDetectorRef,
) {}
) { }
menu: SettingsItem222[] = [
{
title: 'Authentication:',

View File

@ -9,8 +9,8 @@ import { ActivatedRoute, Router } from '@angular/router';
import { Location } from '@angular/common';
import { SessionService } from 'common/service';
import { createLoginState, createPasswordState, getLoginType, isNullOrUndefined } from 'common/utils';
import { AdminUserService, ApplicationService } from 'app/service';
import { SpecificTokenResponse } from 'app/service/application';
import { AdminUserService, ApplicationService } from 'base/service';
import { SpecificTokenResponse } from 'base/service/application';
@Component({
@ -19,10 +19,10 @@ import { SpecificTokenResponse } from 'app/service/application';
styleUrls: ['./sign-in.less'],
})
export class SignInScene implements OnInit {
public loginState: boolean|string = false;
public loginState: boolean | string = false;
public login: string = '';
public passwordState: boolean|string = false;
public passwordState: boolean | string = false;
public password: string = '';
public loginButtonDisabled: boolean = true;
@ -45,7 +45,7 @@ export class SignInScene implements OnInit {
private sessionService: SessionService,
private applicationService: ApplicationService,
private adminUserService: AdminUserService
) {}
) { }
ngOnInit() {
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 { UserService } from 'common/service/user';
import { isNullOrUndefined } from 'common/utils';
import { AdminUserService, ApplicationService } from 'app/service';
import { SpecificReturnResponse } from 'app/service/application';
import { AdminUserService, ApplicationService } from 'base/service';
import { SpecificReturnResponse } from 'base/service/application';
export function checkLoginValidity(value: string): boolean {
let regexCheck = new RegExp('^[a-zA-Z0-9_\\.-]+$');
@ -53,7 +53,7 @@ export class SignOutScene implements OnInit {
private userService: UserService,
private applicationService: ApplicationService,
private adminUserService: AdminUserService
) {}
) { }
ngOnInit() {
const ssoApplicationId = this.route.snapshot.paramMap.get('applicationId');

View File

@ -7,7 +7,7 @@
import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';
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';
@Component({

View File

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

View File

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

View File

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

View File

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

View File

@ -14,13 +14,13 @@ import { SessionService } from './session';
import { SSOService } from './sso';
import { getApplicationLocation, isNullOrUndefined, sha512 } from 'common/utils';
/*
interface MessageLogIn {
login: string;
method: string;
time: number;
password: string;
}
interface MessageAnswer_USER_CONNECT {
sessionId: string;
login: string;
@ -28,7 +28,7 @@ interface MessageAnswer_USER_CONNECT {
role: string;
avatar: string;
}
*/
@Injectable()
export class UserService {
// 0: Not hide password; 1 hide password;
@ -69,9 +69,9 @@ export class UserService {
if (elems.length !== 3) {
return false;
}
//const tokenHeader = decodeURIComponent(window.atob( elems[0] ));
// const tokenHeader = decodeURIComponent(window.atob( elems[0] ));
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);
console.debug(
`Retreive token exp data=${new Date(parsedData.exp * 1000).toISOString()} < ${new Date().toISOString()}`
@ -91,13 +91,13 @@ export class UserService {
*/
checkAutoConnect(): Promise<void> {
let locationOrigin = getApplicationLocation();
let self = this;
const self = this;
return new Promise<void>((resolve, reject) => {
// 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
let pathName = window.location.pathname;
//console.log("start Path-name: '" + pathName + "'");
//console.log("check with: '" + environment.applName + "/sso/" + "'");
// console.log("start Path-name: '" + pathName + "'");
// console.log("check with: '" + environment.applName + "/sso/" + "'");
if (pathName.startsWith('/sso/') || pathName.startsWith(environment.applName + '/sso/')) {
console.log(' ==> SSo section');
reject();
@ -154,7 +154,7 @@ export class UserService {
}
startSession(token: string, rememberMe: boolean): Promise<string> {
let self = this;
const self = this;
return new Promise((resolve, reject) => {
self.retreiveMe(token)
.then((value2: boolean) => {
@ -178,11 +178,11 @@ export class UserService {
}
retreiveMe(token: string): Promise<boolean> {
console.log(`AuthService.loginWithToken ... '${token}'`);
let self = this;
const self = this;
return new Promise((resolve, reject) => {
this.http
.requestJson({
//server: 'karso',
// server: 'karso',
endPoint: 'users/me',
requestType: HTTPRequestModel.GET,
accept: HTTPMimeType.JSON,
@ -193,14 +193,14 @@ export class UserService {
// TODO: check type ...
console.log(`loginWithToken : get some data to check: ${JSON.stringify(response.data)}`);
self.sessionService.create({
sessionId: response.data.sessionId,
//sessionId: response.data.sessionId,
userId: response.data.id,
userLogin: response.data.login,
userEMail: response.data.email,
userAdmin: response.data.admin,
userBlocked: response.data.blocked,
userRemoved: response.data.removed,
userAvatar: response.data.avatar,
//userEMail: response.data.email,
//userAdmin: response.data.admin,
//userBlocked: response.data.blocked,
//userRemoved: response.data.removed,
//userAvatar: response.data.avatar,
tokenJwt: token,
});
resolve(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: 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: {
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,
ssoSignOut: undefined,
ssoSignUp: undefined,

View File

@ -11,7 +11,9 @@ export const environment = {
server: {
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,
ssoSignOut: undefined,
ssoSignUp: undefined,

View File

@ -5,5 +5,9 @@
"baseUrl": "./",
"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,
"experimentalDecorators": true,
"target": "es2018",
"typeRoots": ["node_modules/@types"],
"lib": ["es2018", "dom"],
"typeRoots": [
"node_modules/@types"
],
"lib": [
"es2018",
"dom"
],
"module": "es2020",
"baseUrl": "./src/",
"paths": {
"@app/*": ["./src/app/"],
"@common/*": ["./src/common/"]
"@app-base/*": [
"./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": {
"arrow-return-shorthand": true,
"callable-types": true,
"class-name": true,
"comment-format": [true, "check-space"],
"comment-format": [
true,
"check-space"
],
"curly": true,
"deprecation": {
"severity": "warn"
},
"eofline": true,
"forin": true,
"import-blacklist": [true, "rxjs/Rx"],
"import-blacklist": [
true,
"rxjs/Rx"
],
"import-spacing": true,
"indent": [true, "spaces"],
"indent": [
true,
"tabs"
],
"interface-over-type-literal": true,
"label-position": true,
"max-line-length": [true, 140],
"max-line-length": [
true,
140
],
"member-access": false,
"member-ordering": [
true,
{
"order": ["static-field", "instance-field", "static-method", "instance-method"]
"order": [
"static-field",
"instance-field",
"static-method",
"instance-method"
]
}
],
"no-arg": true,
"no-bitwise": true,
"no-console": [true, "debug", "info", "time", "timeEnd", "trace"],
"no-console": [
true,
"debug",
"info",
"time",
"timeEnd",
"trace"
],
"no-construct": true,
"no-debugger": true,
"no-duplicate-super": true,
"no-empty": false,
"no-empty-interface": true,
"no-eval": true,
"no-inferrable-types": [true, "ignore-params"],
"no-inferrable-types": [
true,
"ignore-params",
"ignore-properties"
],
"no-misused-new": true,
"no-non-null-assertion": true,
"no-shadowed-variable": true,
@ -45,12 +72,27 @@
"no-unused-expression": true,
"no-var-keyword": true,
"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,
"quotemark": [true, "single"],
"quotemark": [
true,
"single"
],
"radix": true,
"semicolon": [true, "always"],
"triple-equals": [true, "allow-null-check"],
"semicolon": [
true,
"always"
],
"triple-equals": [
true,
"allow-null-check"
],
"typedef-whitespace": [
true,
{
@ -63,9 +105,26 @@
],
"unified-signatures": true,
"variable-name": false,
"whitespace": [true, "check-branch", "check-decl", "check-operator", "check-separator", "check-type"],
"directive-selector": [true, "attribute", "app", "camelCase"],
"component-selector": [true, "element", "app", "kebab-case"],
"whitespace": [
true,
"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-inputs-metadata-property": true,
"no-outputs-metadata-property": true,

View File

@ -24,7 +24,7 @@ CREATE USER 'karso'@'%' IDENTIFIED BY 'base_db_password';
GRANT ALL PRIVILEGES ON `karso`.* TO 'karso'@'%';
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