Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Migrate to GeoTools 23.0 #4488

Merged
merged 5 commits into from
May 4, 2020
Merged

Conversation

jusabatier
Copy link
Contributor

@jusabatier jusabatier commented Mar 2, 2020

Modifications for migrate to GeoTools 23.0

Compile OK with mvn clean install
Start without error in JAVA11 / Tomcat9

Still have to test :

  • JAVA8 compatibility
  • Usage tests

Related to #3882

@fxprunayre
Copy link
Member

Don't forget to test WFS feature indexing which was not working (XY order issue) in our last try of updating GT (see #3886)

@jusabatier
Copy link
Contributor Author

Don't understand how I can test it ... :/

@fxprunayre
Copy link
Member

Don't understand how I can test it ... :/

https://geonetwork-opensource.org/manuals/trunk/en/user-guide/analyzing/data.html?highlight=wfs
The easiest is probably to:

@jusabatier
Copy link
Contributor Author

Trying to install ES with your tuto, but where is supposed to be the es/es-config directory ?

@fxprunayre
Copy link
Member

fxprunayre commented Mar 2, 2020

Trying to install ES with your tuto, but where is supposed to be the es/es-config directory ?

https://github.com/geonetwork/core-geonetwork/tree/master/es#install-configure-and-start-elasticsearch

Fixed errors in the doc and updated version number.

@jusabatier
Copy link
Contributor Author

I installed ES, started it, loaded the indices, updated the URL in WEB-INF/config.properties and restarted it.

But when I add a layer to the map and go to filter tab, it says something like "Error accessing index" and I have not button to index the data.

@fxprunayre
Copy link
Member

But when I add a layer to the map and go to filter tab, it says something like "Error accessing index" and I have not button to index the data.

What does
http://localhost:8080/geonetwork/warninghealthcheck (if running from source, you need to build and start the app with mvn jetty:run -Pes to load ES
http://localhost:9200/gn-features
http://localhost:8080/geonetwork/index/features?_=_search
return ?

@jusabatier
Copy link
Contributor Author

I doesn't test it on localhost, I deploy the war on a VM with tomcat9.

http://localhost:8080/geonetwork/warninghealthcheck

= > Error creating bean with name 'EsSearchManager': Unsatisfied dependency expressed through field 'client': No qualifying bean of type [org.fao.geonet.es.EsClient] found for dependency [org.fao.geonet.es.EsClient]

@fxprunayre
Copy link
Member

= > Error creating bean with name 'EsSearchManager': Unsatisfied dependency expressed through field 'client': No qualifying bean of type [org.fao.geonet.es.EsClient] found for dependency [org.fao.geonet.es.EsClient]

So you need to build the app with es profile first.

@jusabatier
Copy link
Contributor Author

With mvn clean install -dskipTests -Pes ?

@jusabatier
Copy link
Contributor Author

Ok it seems to progress :

http://localhost:8080/geonetwork/warninghealthcheck :

[
    {
    "name": "DashboardAppHealthCheck",
    "status": "ERROR",
    "msg": "Dashboard application is not available currently. This component is only required if you use dashboards."
  },
    {
    "name": "DeadlockedThreadsHealthCheck",
    "status": "OK"
  },
    {
    "name": "Free file handles",
    "status": "OK"
  },
    {
    "name": "FreeConnectionsHealthCheck",
    "status": "OK"
  },
    {
    "name": "HarvestersHealthCheck",
    "status": "OK"
  },
    {
    "name": "IndexHealthCheck",
    "status": "OK",
    "msg": "0 records indexed in remote index currently."
  },
    {
    "name": "NoIndexErrorsHealthCheck",
    "status": "OK"
  }
]

Now in filter tab it says something like "Entities not indexed", but I still not have any button to index them.

@fxprunayre
Copy link
Member

fxprunayre commented Mar 2, 2020

With a metadata produced from OGC harvester using https://demo.geo-solutions.it/geoserver ?

Once harvested add USA pop on the map and you should be able to have
image
Click on a feature in the table should zoom to correct location

@jusabatier
Copy link
Contributor Author

Yes.

I tried to harvest both WMS and WMTS, it creates a metadata for WMS/WFS service.

Here is a part the log for WFS :

2020-03-03 08:50:06,504 INFO [TestWFS] - Starting harvesting of TestWFS
2020-03-03 08:50:06,528 INFO [TestWFS] - Started harvesting from node : TestWFS (OgcWxSHarvester)
2020-03-03 08:50:06,528 INFO [TestWFS] - Retrieving remote metadata information for : TestWFS
2020-03-03 08:50:07,217 INFO [TestWFS] - - Number of layers, featureTypes, Coverages or process found : 53
2020-03-03 08:50:07,217 INFO [TestWFS] - - Loading layer: spearfish with UUID 342bb803677d1a5392b59779b3744719deff09d6 (hash of capabilities URL + layer name).
2020-03-03 08:50:07,217 INFO [TestWFS] - - Searching for metadataUrl for layer spearfish
2020-03-03 08:50:07,218 INFO [TestWFS] - - No metadataUrl attribute found for layer 'spearfish'
2020-03-03 08:50:07,253 WARN [TestWFS] - - Failed to load metadata document for layer 'spearfish'. Error is: 'For input string: ""'

I checked create metadata for each layer and it look like layers can't load, but the error message is not very explicit...

I also have a new tab "Data Harvester" which lists jobs for WFS indexations, but it's empty.

@fxprunayre
Copy link
Member

I tried to harvest both WMS and WMTS, it creates a metadata for WMS/WFS service.

Can you check your harvester config, the following works fine for me
image

@jusabatier
Copy link
Contributor Author

I use exactly the same, but still have no layers loaded with this warn in logs :

WARN [wms] - - Failed to load metadata document for layer 'spearfish'. Error is: 'For input string: ""',

@fxprunayre
Copy link
Member

I use exactly the same, but still have no layers loaded with this warn in logs :

Bizarre. Works also fine on https://vanilla.geocat.net/geonetwork/srv/fre/admin.console#/harvest

Can you choose a User in the config ? Error is not super explicit - sounds similar to when the group was mandatory (but it is supposed to be solved in master branch)

@jusabatier
Copy link
Contributor Author

Selecting a user solve the problem, I managed to load all layers, and when add one and go to filter tab, I can index entities.

After index entities, I have new filters on the layer based on fields.

@jusabatier
Copy link
Contributor Author

I think problem you mentioned is not solved, because indexed entities are located in South Pole :(

@fxprunayre
Copy link
Member

Selecting a user solve the problem, I managed to load all layers

Weird (I'll try to have a look to the user issue) and good you made harvesting work.

I think problem you mentioned is not solved, because indexed entities are located in South Pole :(

We tried a couple of options suggested by @jodygarnett #3886 (comment) with no luck in last Bolsena sprint. Would be good to manage to find a solution to move forward on this.

@jusabatier
Copy link
Contributor Author

I tried use of WFSDataStoreFactory.AXIS_ORDER in WFSHarvesterExchangeState like suggested by @jodygarnett and it seems to work well with topp:states layer.

When clear and reindexing features, they are at the right place on the map, and I have no more ES error log related to Y value overflow.

@jusabatier
Copy link
Contributor Author

But not work with layers over Italy like geosolutions:regioni...

@jusabatier jusabatier force-pushed the patch-geotools-22.3 branch from 5d99d81 to 908df9b Compare March 4, 2020 13:25
@jusabatier
Copy link
Contributor Author

After many tests, I manage to force axis order for WGS84 :

if( defaultCRS.equals(epsg4326) && firstAxis.getDirection().absolute() == AxisDirection.NORTH ) {
    config.setAxisOrder(WFSDataStoreFactory.AXIS_ORDER_EAST_NORTH);
    config.initDataStore();
}

And it handle corectly topp:states from https://demo.geo-solutions.it/geoserver

But when trying with geosolutions:regioni which have an EPSG:3044 CRS, it doesn't work.
With some logs, it appears that the code : https://github.com/geonetwork/core-geonetwork/blob/master/workers/wfsfeature-harvester/src/main/java/org/fao/geonet/harvester/wfsfeatures/worker/EsWFSFeatureIndexer.java#L254

Logs of features retieved with getFeatures show coords like this :

  • CRS Id : [EPSG:4326]
    -- Feature Coord :
    x => 4754785.01965227
    y => 625766.32391491

The CRS is updated, but the coordinates still in EPSG:3044, no reprojection done.

Same problem with others SRS like EPSG:26713 of sf:roads layer.

@jusabatier
Copy link
Contributor Author

WIth this commit, it works with both topp:states and geosolutions:regioni from https://demo.geo-solutions.it/geoserver

What I understand searching infos around the web :

  • WGS84 is the EPSG:4326 and is officially defined with latitude/longitude axis order (y/x)
  • Some applications expect WGS84 with longitude/latitude axis order (x/y), ElasticSearch is one of them
  • An unofficial CRS equivalent to WGS84 with longitude/latitude exists : "urn:ogc:def:crs:OGC:1.3:CRS84"
  • GeoServer is anarchic, it return both axis order, depends of the GML version and srsName parameter.

The problem was that the feature reprojection defined in setCoordinateSystemReproject function didn't work, so features sent to ElasticSearch were not in WGS84 but in native CRS.

Moreover, ElasticSearch expects WGS84 with longitude/latitude axis order (x/y), so the best way to get it is to :

For the GeoServer anarchy, I think as the official WGS84 axis order is latitude/longitude (y/x), we should handle only this axis order...

This currently work because we use GML3 and no srsName param.
We should have a problem with axis order in the future if we use GML32 as it return bad axis order for WGS84 and no srsName param.

@jodygarnett
Copy link
Contributor

As part of this bug hunt I documented what geoserver does here

TLDR: Each WFS / WMS specification changes what the EPSG codes mean ... and GeoServer does its best to keep up!

WFS servers (MapServer, deegree, GeoServer, ArcGIS) manage to have every variation of axis order incorrect .. so GeoNetwork will need to provide flags to allow harvester to be configured to connect to each service (there will never be a solution to this only configuration).

@jodygarnett
Copy link
Contributor

@jusabatier see above, configuration options are required.

The previous geotools client did its best to "guess" workarounds; in practice this meant there were always WFS servers we could not talk to. The new client provides additional connection parameters.

@jodygarnett
Copy link
Contributor

I really like this approach, reproject whatever contents is returned to CRS:84 because we cannot trust the different WFS implementations.

It also looks like all features are being requested, so we do not need to worry about different implementations getting axis order confused on the request.

What is needed for this work to go ahead?

@jodygarnett
Copy link
Contributor

For the GeoServer anarchy, I think as the official WGS84 axis order is latitude/longitude (y/x), we should handle only this axis order...

Putting in a kind word for GeoServer here, the anarchy is the specifications, it is actually a real bother to follow what they are doing and implement them "correctly".

If you stay with a specific protocol version (example WFS 2.0 + GML 3.2) the result is consistent. When you mix and match the result is the madness you describe :)

@jusabatier jusabatier changed the title Migrate to GeoTools 22.3 Migrate to GeoTools 23.0 Apr 16, 2020
@jodygarnett
Copy link
Contributor

This is looking good to me, can we rebase this PR and put it up for review?

@@ -1443,7 +1446,7 @@

<!-- NOTE: When updating GeoTools, check which version
of Postgres is used and update pg.version if needed. -->
<geotools.version>22.3</geotools.version>
<geotools.version>23.0</geotools.version>
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should build once more when GeoTools is officially anounced, we are currently having a build issue due to the new osgeo repo ... performing faster and allowing multi-threaded builds to trip on themselves. The Maven local repository is not thread safe apparently ...

@josegar74
Copy link
Member

@jusabatier please if you can fix the conflicts, I'll check to test next week and merge it, thanks.

@jusabatier
Copy link
Contributor Author

I fixed the conflicts.

Compile fine when skipping tests.

But when doing them I have an error :

[ERROR] Failures:
[ERROR] BatchOpsMetadatReindexerTest.asyncMultiThread:127 expected:<4> but was:<3>
[ERROR] Errors:
[ERROR] ApiImportSpatialDirectoryEntriesTest.nominal:38->processLayersZip:102 » NoSuchMethod
[ERROR] ApiImportSpatialDirectoryEntriesTest.withReprojTo3857:67->processLayersZip:102 » NoSuchMethod
[ERROR] ApiImportSpatialDirectoryEntriesTest.withReprojTo4326_IESame:52->processLayersZip:102 » NoSuchMethod

@jodygarnett
Copy link
Contributor

NoSuchMethod seems like we need more information?

Looking at withReprojTo3857:

        processLayersZip("layers_111_feature_EPSG_3857.xml",
                new RequestCustomizer() {
                    @Override
                    public void customizeRequest(MockMultipartHttpServletRequest request) {
                        request.setParameter("schema", "iso19139");
                        request.setParameter("process", "build-extent-subtemplate");
                        request.setParameter("descriptionAttribute", "desc");
                        request.setParameter("onlyBoundingBox", "false");
                        request.setParameter("geomProjectionTo", "EPSG:3857");
                    }
                });

A MockMultipartHttpServletRequest is being setup, and I guess a call is being made to it that was not anticipated...

Looking at processLayersZip:102 shows:

        SimpleMetadataProcessingReport report = (SimpleMetadataProcessingReport) invoker.invoke(request, response);
        assertEquals(200, response.getStatus());
        assertEquals(3, report.

This is an example of mock testing being very fragile :P

@josegar74
Copy link
Member

I get this test error:

[ERROR] Failures: 
[ERROR]   MetadataApiTest.getRelated:581 Status expected:<200> but was:<400>
[INFO] 
[ERROR] Tests run: 377, Failures: 1, Errors: 0, Skipped: 12

With master branch seem ok, to check further.

@jodygarnett
Copy link
Contributor

@josegar74 as in this:

        mockMvc.perform(get("/srv/api/records/" + MAIN_UUID + "/related")
            .session(mockHttpSession)
            .accept(MediaType.APPLICATION_JSON))
            .andExpect(status().isOk())
            .andExpect(content().contentType(API_JSON_EXPECTED_ENCODING));

Do you have the surefire results stack trace anywhere?

@jodygarnett
Copy link
Contributor

@josegar74 running this locally works for me:

[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time:  21:41 min
[INFO] Finished at: 2020-04-29T14:41:31-07:00
[INFO] ------------------------------------------------------------------------

Copy link
Member

@josegar74 josegar74 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The issue with the test seemed some local issue, in travis is passing fine.

@jodygarnett
Copy link
Contributor

Thank you, happy to see this go ahead

Copy link
Member

@fxprunayre fxprunayre left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. Merged in branch 4.0.x too. Thanks.

@fxprunayre
Copy link
Member

fxprunayre commented Jun 16, 2020

It looks like on some setup this introduced this error (happens on different services validation, related resource) - may not be related to this update - I don't really know. On docker with tomcat:8-jre8, one app is running fine. Another one is not.

{"message":"NestedServletException","code":"runtime_exception","description":"Handler dispatch failed; 
nested exception is java.lang.NoClassDefFoundError: 
Could not initialize class com.sun.xml.bind.v2.model.impl.Utils"}

and sounds related to org.glassfish.jaxb:jaxb-runtime:jar

[^[[1;34mINFO^[[m] |  +- org.geotools:gt-wms:jar:23.0:compile
[^[[1;34mINFO^[[m] |  |  +- org.geotools:gt-coverage:jar:23.0:compile
[^[[1;34mINFO^[[m] |  |  |  +- it.geosolutions.imageio-ext:imageio-ext-tiff:jar:1.3.2:compile
[^[[1;34mINFO^[[m] |  |  |  |  +- it.geosolutions.imageio-ext:imageio-ext-utilities:jar:1.3.2:compile
[^[[1;34mINFO^[[m] |  |  |  |  \- it.geosolutions.imageio-ext:imageio-ext-geocore:jar:1.3.2:compile
[^[[1;34mINFO^[[m] |  |  |  |     +- javax.xml.bind:jaxb-api:jar:2.2.11:compile
[^[[1;34mINFO^[[m] |  |  |  |     +- it.geosolutions.imageio-ext:imageio-ext-streams:jar:1.3.2:compile
[^[[1;34mINFO^[[m] |  |  |  |     +- org.glassfish.jaxb:jaxb-runtime:jar:2.4.0-b180830.0438:runtime

The class is also provided by Java rt.jar.

Anyone observing this? Any suggestions?

@jodygarnett
Copy link
Contributor

Anyone observing this? Any suggestions?

It is a common problem ... when upgrading to Java 11 (on newer systems you have to enable jaxb and javax.annotations).

Can you double check what version of Java you are starting up please @fxprunayre?

@fxprunayre
Copy link
Member

What is weird is that it is same WAR based on master deployed on docker with tomcat:8-jre8. So I don't expect that this kind of errors could happen on some and not on other - We have 4 apps deployed for test/prod and only one is having the issue.

@jusabatier
Copy link
Contributor Author

Generaly, it's due to the fact that JAXB APIs are considered to be Java EE APIs and therefore are no longer contained on the default classpath in Java SE 9. In Java 11, they are completely removed from the JDK.

So if you run it on JAVA 8, it should work, but not in JAVA 9 or above.

Here are some solutions : https://stackoverflow.com/questions/43574426/how-to-resolve-java-lang-noclassdeffounderror-javax-xml-bind-jaxbexception-in-j

@pvgenuchten
Copy link

is/will this be backported to 3.10?
i noticed (also in #4072) this patch is required for QGIS metasearch to query geonetwork with a spatial filter

@josegar74
Copy link
Member

No plans to backport this work to 3.10

pmauduit pushed a commit to pmauduit/core-geonetwork that referenced this pull request Sep 29, 2020
* Migrate to GeoTools 22.3

* Correct feature reprojection in WFS indexation

* Upgrade to GeoTools 23.0

* Remove unusefull query and add final statement to close iterator
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants