diff --git a/pom.xml b/pom.xml
index 4e5a4dbd..cc5225e7 100644
--- a/pom.xml
+++ b/pom.xml
@@ -69,8 +69,6 @@
${jersey.version}
-
-
org.apache.logging.log4j
diff --git a/src/main/java/fr/insee/rmes/api/classifications/ClassificationApi.java b/src/main/java/fr/insee/rmes/api/classifications/ClassificationApi.java
index 3f1ec649..49c2c32e 100644
--- a/src/main/java/fr/insee/rmes/api/classifications/ClassificationApi.java
+++ b/src/main/java/fr/insee/rmes/api/classifications/ClassificationApi.java
@@ -16,6 +16,8 @@
import javax.ws.rs.core.Response;
import javax.ws.rs.core.Response.Status;
+import io.swagger.v3.oas.annotations.extensions.Extension;
+import io.swagger.v3.oas.annotations.extensions.ExtensionProperty;
import org.apache.commons.lang3.StringUtils;
import fr.insee.rmes.api.AbstractMetadataApi;
@@ -37,8 +39,7 @@
@Tag(name = "nomenclatures", description = "Nomenclatures API")
public class ClassificationApi extends AbstractMetadataApi {
-
- @Hidden
+
@GET
@Path("/{code}/postes")
@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
diff --git a/src/main/java/fr/insee/rmes/api/geo/AbstractGeoApi.java b/src/main/java/fr/insee/rmes/api/geo/AbstractGeoApi.java
index c5208efb..d5b8678a 100644
--- a/src/main/java/fr/insee/rmes/api/geo/AbstractGeoApi.java
+++ b/src/main/java/fr/insee/rmes/api/geo/AbstractGeoApi.java
@@ -17,6 +17,9 @@
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.List;
+import java.util.Objects;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
public abstract class AbstractGeoApi extends AbstractMetadataApi {
@@ -135,7 +138,11 @@ else if (StringUtils.equalsAnyIgnoreCase(header, MediaType.APPLICATION_JSON)) {
}
protected Response generateBadRequestResponse() {
- return Response.status(Status.BAD_REQUEST).entity("").build();
+ return generateBadRequestResponse("");
+ }
+
+ protected Response generateBadRequestResponse(String erreurMessage) {
+ return Response.status(Status.BAD_REQUEST).entity(erreurMessage).build();
}
// Method to find a list of projections
diff --git a/src/main/java/fr/insee/rmes/api/geo/ConstGeoApi.java b/src/main/java/fr/insee/rmes/api/geo/ConstGeoApi.java
index 0695764b..87344f97 100644
--- a/src/main/java/fr/insee/rmes/api/geo/ConstGeoApi.java
+++ b/src/main/java/fr/insee/rmes/api/geo/ConstGeoApi.java
@@ -10,6 +10,7 @@ public class ConstGeoApi {
public static final String PATH_CIRCO_TER = PATH_SEPARATOR + "circonscriptionTerritoriale";
public static final String PATH_CANTON = PATH_SEPARATOR + "canton";
+ public static final String PATH_IRIS=PATH_SEPARATOR + "iris";
public static final String PATH_COMMUNE = PATH_SEPARATOR + "commune";
public static final String PATH_CANTON_OU_VILLE = PATH_SEPARATOR + "cantonOuVille";
public static final String PATH_PAYS = PATH_SEPARATOR + "pays";
@@ -28,7 +29,7 @@ public class ConstGeoApi {
public static final String PATH_LISTE_CANTON_OU_VILLE= PATH_SEPARATOR +"cantonsEtVilles";
public static final String PATH_INTERCO= PATH_SEPARATOR + "intercommunalite";
public static final String PATH_BASSINDEVIE= PATH_SEPARATOR + "bassinDeVie2022";
-
+ public static final String PATH_LISTE_IRIS = PATH_SEPARATOR + "iris";
public static final String PATH_LISTE_COMMUNE = PATH_SEPARATOR + "communes";
public static final String PATH_LISTE_PAYS = PATH_SEPARATOR + "pays";
public static final String PATH_LISTE_CANTON = PATH_SEPARATOR + "cantons";
@@ -59,6 +60,9 @@ public class ConstGeoApi {
public static final String PATTERN_DISTRICT ="9[78][1-9]{3}";
public static final String PATTERN_INTERCO ="2[0-4][0-9]{7}";
public static final String PATTERN_CANTON = "(([0-9]{2})|(2[0-9AB])|(97[1-6]))([0-9]{2})";
+
+ public static final String PATTERN_IRIS="[0-9][0-9AB][0-9]{7}";
+ public static final String PATTERN_IRIS_DESCRIPTION= "Code Insee de l’Iris (9 caractères)";
public static final String PATTERN_PAYS = "99[0-9]{3}";
public static final String PATTERN_REGION = "[0-9]{2}";
public static final String PATTERN_ZONE_EMPLOI = "[0-9]{4}";
diff --git a/src/main/java/fr/insee/rmes/api/geo/territoire/IrisApi.java b/src/main/java/fr/insee/rmes/api/geo/territoire/IrisApi.java
new file mode 100644
index 00000000..948dbd8c
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/api/geo/territoire/IrisApi.java
@@ -0,0 +1,210 @@
+package fr.insee.rmes.api.geo.territoire;
+
+import fr.insee.rmes.api.geo.AbstractGeoApi;
+import fr.insee.rmes.api.geo.ConstGeoApi;
+import fr.insee.rmes.modeles.geo.territoire.CodeIris;
+import fr.insee.rmes.modeles.geo.territoire.Iris;
+import fr.insee.rmes.modeles.geo.territoire.PseudoIris;
+import fr.insee.rmes.modeles.geo.territoire.Territoire;
+import fr.insee.rmes.modeles.geo.territoires.Territoires;
+import fr.insee.rmes.queries.geo.GeoQueries;
+import fr.insee.rmes.utils.*;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.media.Content;
+import io.swagger.v3.oas.annotations.media.Schema;
+import io.swagger.v3.oas.annotations.responses.ApiResponse;
+import io.swagger.v3.oas.annotations.tags.Tag;
+
+import javax.ws.rs.*;
+import javax.ws.rs.core.HttpHeaders;
+import javax.ws.rs.core.MediaType;
+import javax.ws.rs.core.Response;
+
+
+@Path(ConstGeoApi.PATH_GEO)
+@Tag(name = ConstGeoApi.TAG_NAME, description = ConstGeoApi.TAG_DESCRIPTION)
+public class IrisApi extends AbstractGeoApi {
+ private static final String CODE_PATTERN = "/{code:}";
+ private static final String LITTERAL_PARAMETER_TYPE_DESCRIPTION = "Filtre sur le type de territoire renvoyé.";
+
+ private static final String LITTERAL_RESPONSE_DESCRIPTION = "Iris";
+ private static final String LITTERAL_ID_OPERATION = "getcogiris";
+ private static final String LITTERAL_CODE_EXAMPLE = "010040101";
+ private static final String LITTERAL_PARAMETER_DATE_DESCRIPTION =
+ "Filtre pour renvoyer l'Iris active à la date donnée. Par défaut, c’est la date courante. (Format : 'AAAA-MM-JJ')";
+ private static final String LITTERAL_OPERATION_SUMMARY =
+ "Informations sur un Iris identifié par son code (neuf chiffres pour la métropole ou 2A/2B plus 7 chiffres pour la Corse)";
+
+
+ private final IrisUtils irisUtils;
+
+ public IrisApi() {
+ // Constructeur par défaut
+ this.irisUtils = new IrisUtils();
+ }
+
+ protected IrisApi(SparqlUtils sparqlUtils, CSVUtils csvUtils, ResponseUtils responseUtils, IrisUtils irisUtils) {
+ super(sparqlUtils, csvUtils, responseUtils);
+ this.irisUtils = irisUtils;
+ }
+
+ @Path(ConstGeoApi.PATH_IRIS + CODE_PATTERN)
+ @GET
+ @Produces({
+ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML
+ })
+ @Operation(operationId = LITTERAL_ID_OPERATION, summary = LITTERAL_OPERATION_SUMMARY, responses = {
+ @ApiResponse(
+ content = @Content(schema = @Schema(implementation = Iris.class)),
+ description = LITTERAL_RESPONSE_DESCRIPTION)
+
+ })
+ public Response getByCode(
+ @Parameter(
+ description = ConstGeoApi.PATTERN_IRIS_DESCRIPTION,
+ required = true,
+ schema = @Schema(
+ pattern = ConstGeoApi.PATTERN_IRIS,
+ type = Constants.TYPE_STRING, example = LITTERAL_CODE_EXAMPLE)) @PathParam(Constants.CODE) String code,
+ @Parameter(hidden = true) @HeaderParam(HttpHeaders.ACCEPT) String header,
+ @Parameter(
+ description = LITTERAL_PARAMETER_DATE_DESCRIPTION,
+ schema = @Schema(type = Constants.TYPE_STRING, format = Constants.FORMAT_DATE)) @QueryParam(
+ value = Constants.PARAMETER_DATE) String date) {
+
+ var codeIris = CodeIris.of(code);
+ if (codeIris.isInvalid()) {
+ return generateBadRequestResponse(ConstGeoApi.ERREUR_PATTERN);
+ }
+ if (!this.verifyParameterDateIsRightWithoutHistory(date)) {
+ return this.generateBadRequestResponse();
+ }
+
+ return getResponseForIrisOrPseudoIris(codeIris, header, date);
+ }
+
+ private Response getResponseForIrisOrPseudoIris(CodeIris codeIris, String header, String date) {
+ if (irisUtils.hasIrisDescendant(codeIris.codeCommune())) {
+ return getResponseForIris(codeIris, header, date);
+ } else {
+ return getResponseForPseudoIris(codeIris, header, date);
+ }
+
+ }
+
+ private Response getResponseForPseudoIris(CodeIris codeIris, String header, String date) {
+ if (codeIris.isPseudoIrisCode()) {
+ return this.generateResponseATerritoireByCode(
+ sparqlUtils.executeSparqlQuery(
+ GeoQueries.getIrisByCodeAndDate(codeIris.code(), this.formatValidParameterDateIfIsNull(date))),
+ header,
+ new PseudoIris(codeIris.code()));
+ } else {
+ return Response.status(Response.Status.NOT_FOUND).entity("").build();
+ }
+ }
+
+ private Response getResponseForIris(CodeIris codeIris, String header, String date) {
+ if (codeIris.isPseudoIrisCode()) {
+ return Response.status(Response.Status.NOT_FOUND).entity("").build();
+ } else {
+ Territoire territoire = new Iris(codeIris.code());
+ return this.generateResponseATerritoireByCode(
+ sparqlUtils.executeSparqlQuery(
+ GeoQueries.getIrisByCodeAndDate(codeIris.code(), this.formatValidParameterDateIfIsNull(date))),
+ header,
+ territoire);
+ }
+ }
+
+
+ @Path(ConstGeoApi.PATH_LISTE_IRIS)
+ @GET
+ @Produces({
+ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML
+ })
+ @Operation(
+ operationId = LITTERAL_ID_OPERATION + ConstGeoApi.ID_OPERATION_LISTE,
+ summary = "Informations sur toutes les iris actifs à la date donnée. Par défaut, c’est la date courante.",
+ responses = {
+ @ApiResponse(
+ content = @Content(schema = @Schema(type = ARRAY, implementation = Territoire.class)),
+ description = LITTERAL_RESPONSE_DESCRIPTION)
+ })
+ public Response getListe(
+ @Parameter(hidden = true) @HeaderParam(HttpHeaders.ACCEPT) String header,
+ @Parameter(
+ description = "Filtre pour renvoyer les Iris ou faux-Iris à la date donnée. Par défaut, c’est la date courante. (Format : 'AAAA-MM-JJ')",
+ schema = @Schema(type = Constants.TYPE_STRING, format = Constants.FORMAT_DATE)) @QueryParam(
+ value = Constants.PARAMETER_DATE) String date,
+ @Parameter(description = "les Iris (et pseudo-iris) des collectivités d'outre-mer",
+ required = true,
+ schema = @Schema(type = Constants.TYPE_BOOLEAN, allowableValues = {"true", "false"}, example = "false", defaultValue = "false"))
+ @QueryParam(
+ value = Constants.PARAMETER_STRING) Boolean com
+ ) {
+
+ if (!this.verifyParameterDateIsRightWithHistory(date)) {
+ return this.generateBadRequestResponse();
+ } else {
+ return this
+ .generateResponseListOfTerritoire(
+ sparqlUtils
+ .executeSparqlQuery(GeoQueries.getListIris(this.formatValidParameterDateIfIsNull(date), this.formatValidParameterBooleanIfIsNull(com))),
+ header,
+ Territoires.class,
+ Territoire.class);
+ }
+ }
+
+
+ @Path(ConstGeoApi.PATH_IRIS + CODE_PATTERN + ConstGeoApi.PATH_ASCENDANT)
+ @GET
+ @Produces({
+ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML
+ })
+ @Operation(
+ operationId = LITTERAL_ID_OPERATION + ConstGeoApi.ID_OPERATION_ASCENDANTS,
+ summary = "Informations concernant les territoires qui contiennent l'Iris",
+ responses = {
+ @ApiResponse(
+ content = @Content(schema = @Schema(type = ARRAY, implementation = Territoire.class)),
+ description = LITTERAL_RESPONSE_DESCRIPTION)
+ })
+ public Response getAscendants(
+ @Parameter(
+ description = ConstGeoApi.PATTERN_IRIS_DESCRIPTION,
+ required = true,
+ schema = @Schema(
+ pattern = ConstGeoApi.PATTERN_IRIS,
+ type = Constants.TYPE_STRING, example = LITTERAL_CODE_EXAMPLE)) @PathParam(Constants.CODE) String code,
+ @Parameter(hidden = true) @HeaderParam(HttpHeaders.ACCEPT) String header,
+ @Parameter(
+ description = "Filtre pour renvoyer les territoires contenant l'iris actif à la date donnée. Par défaut, c’est la date courante. (Format : 'AAAA-MM-JJ')",
+ schema = @Schema(type = Constants.TYPE_STRING, format = Constants.FORMAT_DATE)) @QueryParam(
+ value = Constants.PARAMETER_DATE) String date,
+ @Parameter(
+ description = LITTERAL_PARAMETER_TYPE_DESCRIPTION,
+ schema = @Schema(type = Constants.TYPE_STRING)) @QueryParam(
+ value = Constants.PARAMETER_TYPE) String typeTerritoire) {
+
+ if (!this.verifyParametersTypeAndDateAreValid(typeTerritoire, date)) {
+ return this.generateBadRequestResponse();
+ } else {
+ return this
+ .generateResponseListOfTerritoire(
+ sparqlUtils
+ .executeSparqlQuery(
+ GeoQueries
+ .getAscendantsIris(
+ code,
+ this.formatValidParameterDateIfIsNull(date),
+ this.formatValidParametertypeTerritoireIfIsNull(typeTerritoire))),
+ header,
+ Territoires.class,
+ Territoire.class);
+ }
+ }
+
+}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/EnumTypeGeographie.java b/src/main/java/fr/insee/rmes/modeles/geo/EnumTypeGeographie.java
index cd440e5d..44eb99c9 100644
--- a/src/main/java/fr/insee/rmes/modeles/geo/EnumTypeGeographie.java
+++ b/src/main/java/fr/insee/rmes/modeles/geo/EnumTypeGeographie.java
@@ -1,12 +1,12 @@
package fr.insee.rmes.modeles.geo;
-import java.util.Optional;
-import java.util.stream.Stream;
-
import fr.insee.rmes.modeles.geo.territoire.*;
import fr.insee.rmes.modeles.geo.territoires.*;
import fr.insee.rmes.utils.Constants;
+import java.util.Optional;
+import java.util.stream.Stream;
+
public enum EnumTypeGeographie {
COMMUNE("Commune", Commune.class,Communes.class, Constants.NONE),
@@ -25,8 +25,8 @@ public enum EnumTypeGeographie {
DISTRICT("District",District.class,Districts.class,Constants.NONE),
CIRCONSCRIPTION_TERRITORIALE("CirconscriptionTerritoriale",CirconscriptionTerritoriale.class,CirconscriptionsTerritoriales.class,Constants.NONE),
INTERCOMMUNALITE("Intercommunalite",Intercommunalite.class,Intercommunalites.class,Constants.NONE),
- BASSINDEVIE("BassinDeVie2022",BassinDeVie2022.class,BassinsDeVie2022.class,Constants.NONE);
-
+ BASSINDEVIE("BassinDeVie2022",BassinDeVie2022.class,BassinsDeVie2022.class,Constants.NONE),
+ IRIS("Iris", Iris.class,Iriss.class,Constants.NONE);
private String typeObjetGeo;
private Class extends Territoire> classNameOfGeoType;
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/IntituleSansArticle.java b/src/main/java/fr/insee/rmes/modeles/geo/IntituleSansArticle.java
index 7e735a6a..fa36ade8 100644
--- a/src/main/java/fr/insee/rmes/modeles/geo/IntituleSansArticle.java
+++ b/src/main/java/fr/insee/rmes/modeles/geo/IntituleSansArticle.java
@@ -1,26 +1,23 @@
package fr.insee.rmes.modeles.geo;
-import javax.xml.bind.annotation.XmlAccessType;
-import javax.xml.bind.annotation.XmlAccessorType;
-import javax.xml.bind.annotation.XmlAttribute;
-import javax.xml.bind.annotation.XmlRootElement;
-import javax.xml.bind.annotation.XmlValue;
-
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonPropertyOrder;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlText;
-
import io.swagger.v3.oas.annotations.media.Schema;
+import javax.xml.bind.annotation.*;
+
@Schema(description="Intitulé sans son article et article associé")
@XmlAccessorType(XmlAccessType.PROPERTY)
@JsonPropertyOrder({"intituleSansArticle", "typeArticle"})
-@XmlRootElement(name="IntituleSansArticle")
+@XmlRootElement(name = "IntituleSansArticle")
+@JacksonXmlRootElement(localName = "IntituleSansArticle")
public class IntituleSansArticle {
- //@Schema(example = "Aigle")
- @XmlValue
+ @Schema(example = "Aigle")
+ //@XmlValue
private String label = null;
@Schema(example = "5")
@@ -28,8 +25,8 @@ public class IntituleSansArticle {
@JacksonXmlText
- // @JsonProperty("intituleSansArticle")
- // @JacksonXmlProperty(localName="intituleSansArticle")
+ @JsonProperty("intituleSansArticle")
+ @JacksonXmlProperty(localName="IntituleSansArticle")
@Schema(example = "Aigle")
@XmlValue
public String getIntituleSansArticle() {
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/CodeIris.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/CodeIris.java
new file mode 100644
index 00000000..cb7e2edb
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/CodeIris.java
@@ -0,0 +1,41 @@
+package fr.insee.rmes.modeles.geo.territoire;
+
+import java.util.regex.Pattern;
+
+import static fr.insee.rmes.api.geo.ConstGeoApi.PATTERN_IRIS;
+
+public final class CodeIris {
+
+ private static final Pattern IRIS_CODE_PATTERN = Pattern.compile(PATTERN_IRIS);
+ public static final String PSEUDO_IRIS_SUFFIX = "0000";
+ private final String code;
+ private final boolean isInvalid;
+
+ private CodeIris(String code) {
+ this.code = code;
+ isInvalid = ! IRIS_CODE_PATTERN.matcher(code).matches();
+ }
+
+ public static CodeIris of(String code) {
+ return new CodeIris(code);
+ }
+
+ public boolean isInvalid() {
+ return this.isInvalid;
+ }
+
+ public String code() {
+ if (isInvalid){
+ throw new IllegalStateException("Cannot get an invalid code (which does not match "+PATTERN_IRIS+") from CodeIris");
+ }
+ return code;
+ }
+
+ public boolean isPseudoIrisCode() {
+ return code().endsWith(PSEUDO_IRIS_SUFFIX);
+ }
+
+ public String codeCommune() {
+ return code().substring(0, 5);
+ }
+}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/Commune.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Commune.java
index 23c1b96f..fbacf409 100644
--- a/src/main/java/fr/insee/rmes/modeles/geo/territoire/Commune.java
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Commune.java
@@ -1,19 +1,18 @@
package fr.insee.rmes.modeles.geo.territoire;
-import javax.validation.constraints.NotNull;
-import javax.xml.bind.annotation.XmlAccessType;
-import javax.xml.bind.annotation.XmlAccessorType;
-import javax.xml.bind.annotation.XmlRootElement;
-
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
-
import fr.insee.rmes.modeles.geo.EnumTypeGeographie;
import fr.insee.rmes.modeles.geo.IntituleSansArticle;
import io.swagger.v3.oas.annotations.media.Schema;
+import javax.validation.constraints.NotNull;
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlRootElement;
+
@XmlRootElement(name = "Commune")
@JacksonXmlRootElement(localName = "Commune")
@XmlAccessorType(XmlAccessType.FIELD)
@@ -30,11 +29,13 @@ public Commune() {
this.inclusion=null;
}
+
public Commune(String code) {
this();
this.code = code;
}
+
@Override
@JacksonXmlProperty(isAttribute = true)
@Schema(example = "55323")
@@ -89,4 +90,5 @@ public Inclusion getInclusion() {
}
+
}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/Iris.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Iris.java
new file mode 100644
index 00000000..a5c21c85
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Iris.java
@@ -0,0 +1,107 @@
+package fr.insee.rmes.modeles.geo.territoire;
+
+import com.fasterxml.jackson.annotation.JsonProperty;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
+import fr.insee.rmes.modeles.geo.EnumTypeGeographie;
+import fr.insee.rmes.modeles.geo.IntituleSansArticle;
+import io.swagger.v3.oas.annotations.media.Schema;
+
+import javax.validation.constraints.NotNull;
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlRootElement;
+
+@XmlRootElement(name = "Iris")
+@JacksonXmlRootElement(localName = "Iris")
+@XmlAccessorType(XmlAccessType.FIELD)
+@Schema(description = "Objet représentant un Iris")
+public class Iris extends Territoire {
+
+ private final TypeDIris typeDIris;
+
+ public Iris(
+ TypeDIris typeDIris,
+ String code,
+ String uri,
+ String intitule,
+ String dateCreation,
+ String dateSuppression,
+ IntituleSansArticle intituleSansArticle) {
+ super(code, uri, intitule, EnumTypeGeographie.IRIS.getTypeObjetGeo(), dateCreation, dateSuppression, intituleSansArticle);
+ this.typeDIris=typeDIris;
+ }
+
+ public Iris() {
+ this(null);
+ }
+
+ public Iris(String code) {
+ this(null, code, null, null, null, null, new IntituleSansArticle());
+ }
+
+
+ @Override
+ @JacksonXmlProperty(localName = "Type")
+ @Schema(example = "http://rdf.insee.fr/def/geo#Iris")
+ public String getType() {
+ return type;
+ }
+
+ @Override
+ @JacksonXmlProperty(isAttribute = true)
+ @Schema(example = "010040101")
+ public String getCode() {
+ return code;
+ }
+
+ @Override
+ @JacksonXmlProperty(isAttribute = true)
+ @Schema(description = "URI de l'Iris ", example = "http://id.insee.fr/geo/iris/b8c772de-9551-4f13-81c5-eca5bb0f2f7d")
+ public String getUri() {
+ return uri;
+ }
+
+ @Override
+ @JacksonXmlProperty(localName = "Intitule")
+ @JsonProperty(value = "intitule")
+ @Schema(description = "Nom de l'Iris (avec article)", example = "Les Pérouses-Triangle d'Activités")
+ public String getIntitule() {
+ return intitule;
+ }
+
+ @Override
+ @JacksonXmlProperty(localName = "IntituleSansArticle")
+ @JsonProperty(value = "intituleSansArticle")
+ @Schema(description = "Nom de l'Iris sans article", example = "Pérouses-Triangle d'Activité")
+ public IntituleSansArticle getIntituleSansArticle() {
+ return intituleSansArticle;
+ }
+
+
+ @JacksonXmlProperty(localName = "TypeDIris")
+ @NotNull
+ @Schema(description = "Type d'Iris (H , A ou D)", example = "H")
+ public TypeDIris getTypeDIris() {
+ return typeDIris;
+ }
+
+
+ @Override
+ @JacksonXmlProperty(localName = "DateCreation")
+ @Schema(
+ description = "Date de création de l'Iris si il n’existait pas au premier COG du 1er janvier 2016",
+ example = "2016-01-01")
+ public String getDateCreation() {
+ return dateCreation;
+ }
+
+ @Override
+ @JacksonXmlProperty(localName = "DateSuppression")
+ @Schema(description = "Date de suppression de l'Iris si il a été supprimé. ", example = "2019-01-01")
+ public String getDateSuppression() {
+ return dateSuppression;
+ }
+
+ // getters and setters
+}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/PseudoIris.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/PseudoIris.java
new file mode 100644
index 00000000..033ea75b
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/PseudoIris.java
@@ -0,0 +1,104 @@
+package fr.insee.rmes.modeles.geo.territoire;
+
+
+import com.fasterxml.jackson.annotation.JsonInclude;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
+import fr.insee.rmes.modeles.geo.EnumTypeGeographie;
+import fr.insee.rmes.modeles.geo.IntituleSansArticle;
+
+import javax.xml.bind.annotation.*;
+
+@XmlRootElement(name = "Commune")
+@JacksonXmlRootElement(localName = "Commune")
+@XmlAccessorType(XmlAccessType.FIELD)
+@JsonInclude(JsonInclude.Include.NON_EMPTY)
+public class PseudoIris extends Territoire{
+
+ public PseudoIris(
+ String code,
+ String uri,
+ String intitule,
+ String dateCreation,
+ String dateSuppression,
+ IntituleSansArticle intituleSansArticle) {
+ super(code, uri, intitule, EnumTypeGeographie.COMMUNE.getTypeObjetGeo(), dateCreation, dateSuppression, intituleSansArticle);
+ }
+
+ public PseudoIris() {
+ this(null);
+ }
+
+ public PseudoIris(String code) {
+ this(code, null, null, null, null, new IntituleSansArticle());
+ }
+
+
+
+ public String getCode() {
+ return code;
+ }
+
+ public void setCode(String code) {
+ if (this.code==null) {
+ this.code=code;
+ }
+ }
+
+
+ public String getUri() {
+ return uri;
+ }
+
+ public void setUri(String uri) {
+ this.uri = uri;
+ }
+
+
+ public String getIntitule() {
+ return intitule;
+ }
+
+ public void setIntitule(String intitule) {
+ this.intitule = intitule;
+ }
+
+
+ public String getType() {
+ return type;
+ }
+
+ public void setType(String type) {
+ this.type = type;
+ }
+
+
+ public String getDateCreation() {
+ return dateCreation;
+ }
+
+ public void setDateCreation(String dateCreation) {
+ this.dateCreation = dateCreation;
+ }
+
+
+ public String getDateSuppression() {
+ return dateSuppression;
+ }
+
+ public void setDateSuppression(String dateSuppression) {
+ this.dateSuppression = dateSuppression;
+ }
+
+ @Override
+ public String toString() {
+ return "PseudoIris{" +
+ "code='" + code + '\'' +
+ ", uri='" + uri + '\'' +
+ ", intitule='" + intitule + '\'' +
+ ", type='" + type + '\'' +
+ ", dateCreation='" + dateCreation + '\'' +
+ ", dateSuppression='" + dateSuppression + '\'' +
+ ", intituleSansArticle=" + intituleSansArticle +
+ '}';
+ }
+}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/Territoire.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Territoire.java
index 7e19c4e6..4d3be9f6 100644
--- a/src/main/java/fr/insee/rmes/modeles/geo/territoire/Territoire.java
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/Territoire.java
@@ -1,29 +1,28 @@
package fr.insee.rmes.modeles.geo.territoire;
-import javax.xml.bind.annotation.XmlAttribute;
-import javax.xml.bind.annotation.XmlElement;
-import javax.xml.bind.annotation.XmlRootElement;
-
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonInclude.Include;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
-
import fr.insee.rmes.modeles.geo.IntituleSansArticle;
import io.swagger.v3.oas.annotations.media.Schema;
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlRootElement;
+
@XmlRootElement(name="Territoire")
public abstract class Territoire {
@XmlAttribute
protected String code = null;
-
+
@XmlAttribute
protected String uri = null;
-
+
@XmlElement(name="Intitule")
protected String intitule = null;
-
+
@XmlElement(name="Type")
protected String type;
@@ -42,11 +41,10 @@ public abstract class Territoire {
@JsonInclude(Include.NON_EMPTY)
@XmlElement(name="ChefLieu")
protected String chefLieu = null;
-
+
@JsonInclude(Include.NON_EMPTY)
@XmlElement(name="CategorieJuridique")
protected String categorieJuridique = null;
-
@JacksonXmlProperty(isAttribute = true)
public String getCode() {
@@ -76,13 +74,7 @@ public Territoire(
IntituleSansArticle intituleSansArticle,
String chefLieu) {
- this.code = code;
- this.uri = uri;
- this.intitule = intitule;
- this.type = type;
- this.dateCreation = dateCreation;
- this.dateSuppression = dateSuppression;
- this.intituleSansArticle = intituleSansArticle;
+ this(code, uri, intitule, type, dateCreation, dateSuppression, null, intituleSansArticle);
this.chefLieu = chefLieu;
}
@@ -95,15 +87,9 @@ public Territoire(
String dateSuppression,
IntituleSansArticle intituleSansArticle) {
- this.code = code;
- this.uri = uri;
- this.intitule = intitule;
- this.type = type;
- this.dateCreation = dateCreation;
- this.dateSuppression = dateSuppression;
- this.intituleSansArticle = intituleSansArticle;
+ this(code, uri, intitule, type, dateCreation, dateSuppression, null, intituleSansArticle);
}
-
+
public Territoire(
String code,
String uri,
@@ -124,9 +110,9 @@ public Territoire(
this.intituleSansArticle = intituleSansArticle;
this.categorieJuridique= categorieJuridique;
}
-
+
public Territoire() {
- this.intituleSansArticle = new IntituleSansArticle();
+ this(null);
}
public Territoire(String code) {
@@ -153,6 +139,7 @@ public void setType(String type) {
this.type = type;
}
+
@JacksonXmlProperty(localName = "DateCreation")
public String getDateCreation() {
return dateCreation;
@@ -170,7 +157,6 @@ public String getDateSuppression() {
public void setDateSuppression(String dateSuppression) {
this.dateSuppression = dateSuppression;
}
-
@JacksonXmlProperty(localName = "IntituleSansArticle")
public IntituleSansArticle getIntituleSansArticle() {
return intituleSansArticle;
@@ -197,7 +183,7 @@ public void setChefLieu(String chefLieu) {
this.chefLieu = chefLieu;
}
-
+
@JacksonXmlProperty(localName = "CategorieJuridique")
public String getCategorieJuridique() {
return categorieJuridique;
@@ -206,5 +192,6 @@ public String getCategorieJuridique() {
public void setCategorieJuridique(String categorieJuridique) {
this.categorieJuridique = categorieJuridique;
}
-
+
+
}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoire/TypeDIris.java b/src/main/java/fr/insee/rmes/modeles/geo/territoire/TypeDIris.java
new file mode 100644
index 00000000..166552fd
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoire/TypeDIris.java
@@ -0,0 +1,19 @@
+package fr.insee.rmes.modeles.geo.territoire;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.fasterxml.jackson.annotation.JsonValue;
+
+import javax.xml.bind.annotation.XmlValue;
+
+@JsonFormat(shape = JsonFormat.Shape.STRING)
+public enum TypeDIris {
+ H, A, D;
+
+ @JsonValue
+ @XmlValue
+ @Override
+ public String toString(){
+ return name();
+ }
+
+}
diff --git a/src/main/java/fr/insee/rmes/modeles/geo/territoires/Iriss.java b/src/main/java/fr/insee/rmes/modeles/geo/territoires/Iriss.java
new file mode 100644
index 00000000..4285bd0a
--- /dev/null
+++ b/src/main/java/fr/insee/rmes/modeles/geo/territoires/Iriss.java
@@ -0,0 +1,32 @@
+package fr.insee.rmes.modeles.geo.territoires;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty;
+import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
+import fr.insee.rmes.modeles.geo.territoire.Iris;
+import io.swagger.v3.oas.annotations.media.Schema;
+
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import java.util.List;
+@JacksonXmlRootElement(localName = "Iriss")
+@XmlAccessorType(XmlAccessType.FIELD)
+@Schema(name = "Iriss", description = "Tableau représentant les Iriss")
+public class Iriss extends Territoires{
+ private List iriss = null;
+
+ public Iriss() {}
+
+ public Iriss(List iriss) {
+ this.iriss = iriss;
+ }
+
+ @JacksonXmlProperty(isAttribute = true, localName = "Iris")
+ @JacksonXmlElementWrapper(useWrapping = false)
+ public List getIriss() {
+ return iriss;
+ }
+
+ public void setIriss(List cantons) {
+ this.iriss = iriss;
+ }
+}
diff --git a/src/main/java/fr/insee/rmes/queries/geo/GeoQueries.java b/src/main/java/fr/insee/rmes/queries/geo/GeoQueries.java
index 0fa08a19..232b1f8f 100644
--- a/src/main/java/fr/insee/rmes/queries/geo/GeoQueries.java
+++ b/src/main/java/fr/insee/rmes/queries/geo/GeoQueries.java
@@ -1,13 +1,12 @@
package fr.insee.rmes.queries.geo;
-import java.util.HashMap;
-import java.util.Map;
-
-import fr.insee.rmes.config.Configuration;
import fr.insee.rmes.modeles.geo.EnumTypeGeographie;
import fr.insee.rmes.queries.Queries;
import fr.insee.rmes.utils.Constants;
+import java.util.HashMap;
+import java.util.Map;
+
public class GeoQueries extends Queries {
private static final String CODE = "code";
@@ -71,6 +70,13 @@ public static String getCantonByCodeAndDate(String code, String date) {
return getTerritoire(code, date, EnumTypeGeographie.CANTON);
}
+ public static String getIrisByCodeAndDate(String code,String date) {
+ if (code.endsWith("0000")) {
+ return getTerritoire(code.substring(0,5), date, EnumTypeGeographie.COMMUNE);}
+ else {
+ return getTerritoire(code, date, EnumTypeGeographie.IRIS);
+ }
+ }
public static String getCantonOuVilleByCodeAndDate(String code, String date) {
return getTerritoire(code, date, EnumTypeGeographie.CANTON_OU_VILLE);
}
@@ -119,6 +125,9 @@ public static String getListCantonsOuVilles(String date) {
return getTerritoire(Constants.NONE, date, EnumTypeGeographie.CANTON_OU_VILLE);
}
+ public static String getListIris(String date,Boolean com) {
+ return getTerritoireListIris(Constants.NONE, date,EnumTypeGeographie.IRIS,com);
+ }
public static String getListCantons(String date){
return getTerritoire(Constants.NONE,date,EnumTypeGeographie.CANTON);
}
@@ -162,7 +171,9 @@ public static String getAscendantsDepartement(String code, String date, String t
public static String getAscendantsCanton(String code, String date, String type) {
return getAscendantOrDescendantsQuery(code, date, type, EnumTypeGeographie.CANTON,Constants.ABSENT,Constants.NONE, true);
}
-
+ public static String getAscendantsIris(String code, String date, String type) {
+ return getAscendantOrDescendantsQuery(code, date, type, EnumTypeGeographie.IRIS,Constants.ABSENT,Constants.NONE, true);
+ }
public static String getAscendantsDistrict(String code, String date, String type) {
return getAscendantOrDescendantsQuery(code, date, type, EnumTypeGeographie.DISTRICT,Constants.ABSENT,Constants.NONE,true);
}
@@ -415,7 +426,11 @@ private static String getAscendantOrDescendantsQuery(
params.put(FILTRE, filtreNom);
params.put(COM,com);
params.put(ASCENDANT, String.valueOf(ascendant));
- return buildRequest(QUERIES_FOLDER, "getAscendantsOrDescendantsByCodeTypeDate.ftlh", params);
+ if(code.matches("^.{5}0000$") && typeOrigine.getTypeObjetGeo().equals("Iris")) {
+ return buildRequest(QUERIES_FOLDER, "getAscendantsIrisByCodeTypeDate.ftlh", params);
+ } else {
+ return buildRequest(QUERIES_FOLDER, "getAscendantsOrDescendantsByCodeTypeDate.ftlh", params);
+ }
}
@@ -431,17 +446,39 @@ private static String getPreviousOrNextQuery(
}
private static String getTerritoire(String code, String date, EnumTypeGeographie typeGeo) {
- return getTerritoireFiltre(code,date,Constants.ABSENT,typeGeo,true);
+ if (typeGeo == EnumTypeGeographie.IRIS && code !="none") {
+ return getIris(code, date,typeGeo);
+ } else{
+ return getTerritoireFiltre(code, date, Constants.ABSENT, typeGeo, true);
+ }
}
+ private static String getTerritoireListIris(String code, String date, EnumTypeGeographie typeGeo,Boolean com) {
+ if (com.booleanValue()==true) {
+ return getIrisList(code, date,typeGeo,true);
+ } else {
+ return getIrisList(code, date, typeGeo, false);
+ }
+ }
private static Map buildCodeAndDateParams(String code, String date) {
Map params = new HashMap<>();
params.put(CODE, code);
params.put(DATE, date);
return params;
}
-
-
+
+ private static String getIris(String code, String date, EnumTypeGeographie typeGeo) {
+ Map params = buildCodeAndDateParams(code, date);
+ params.put("territoire", typeGeo.getTypeObjetGeo());
+ return buildRequest(QUERIES_FOLDER, "getIrisByCodeDate.ftlh", params);
+
+ }
+
+ private static String getIrisList(String code, String date, EnumTypeGeographie typeGeo,boolean com){
+ Map params = buildCodeAndDateAndFilterParams(code, date,Constants.NONE, com);
+ params.put("territoire", typeGeo.getTypeObjetGeo());
+ return buildRequest(QUERIES_FOLDER, "getIrisList.ftlh",params);
+ }
private static String getTerritoireFiltre(String code, String date, String filtreNom, EnumTypeGeographie typeGeo,boolean com) {
Map params = buildCodeAndDateAndFilterParams(code, date, filtreNom,com);
params.put("territoire", typeGeo.getTypeObjetGeo());
@@ -459,22 +496,18 @@ private static Map buildCodeAndDateAndFilterParams(String code,
}
public static String getCountry(String code) {
- return "SELECT ?uri ?intitule ?intituleEntier \n"
- + "FROM \n"
- + "WHERE { \n"
- + "?uri rdf:type igeo:Etat . \n"
- + "?uri igeo:codeINSEE '"
- + code
- + "' . \n"
- + "?uri igeo:nom ?intitule . \n"
- + "?uri igeo:nomEntier ?intituleEntier . \n"
- // Ensure that is not the dbpedia URI
- + "FILTER (REGEX(STR(?uri), '"
- + Configuration.getBaseHost()
- + "')) \n"
- + "FILTER (lang(?intitule) = 'fr') \n"
- + "FILTER (lang(?intituleEntier) = 'fr') \n"
- + "}";
+ return String.format(
+ "SELECT ?uri ?intitule ?intituleEntier ?code \n"
+ + "FROM \n"
+ + "WHERE { \n"
+ + " ?urilong a igeo:Pays ; \n"
+ + " igeo:codeINSEE \"%s\" ; \n"
+ + " igeo:nom ?intitule; \n"
+ + " owl:sameAs ?uri; \n"
+ + " igeo:nomLong ?intituleEntier . \n"
+ + " BIND(\"%s\" AS ?code)\n"
+ + " FILTER (REGEX(STR(?uri), \"http://id.insee.fr\")) \n"
+ + "}", code, code);
}
diff --git a/src/main/java/fr/insee/rmes/utils/CSVUtils.java b/src/main/java/fr/insee/rmes/utils/CSVUtils.java
index f3a3e09d..c6e2343b 100644
--- a/src/main/java/fr/insee/rmes/utils/CSVUtils.java
+++ b/src/main/java/fr/insee/rmes/utils/CSVUtils.java
@@ -3,6 +3,9 @@
import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.MapperFeature;
import com.fasterxml.jackson.databind.MappingIterator;
+import com.fasterxml.jackson.databind.cfg.CoercionAction;
+import com.fasterxml.jackson.databind.cfg.CoercionInputShape;
+import com.fasterxml.jackson.databind.type.LogicalType;
import com.fasterxml.jackson.dataformat.csv.CsvMapper;
import com.fasterxml.jackson.dataformat.csv.CsvSchema;
import fr.insee.rmes.modeles.geo.EnumTypeGeographie;
@@ -52,6 +55,9 @@ private List csvToMultiPOJO(String csv, Class childClass) throws IOExc
CsvMapper mapper = CsvMapper.csvBuilder().enable(MapperFeature.ACCEPT_CASE_INSENSITIVE_ENUMS)
.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES)
.build();
+ // Activer la coercition pour les chaînes vides vers null pour toutes les propriétés d'énumération
+ mapper.coercionConfigFor(LogicalType.Enum)
+ .setCoercion(CoercionInputShape.EmptyString, CoercionAction.AsNull);
CsvSchema schema = CsvSchema.emptySchema().withHeader();
MappingIterator