{"action":"created","comment":{"url":"https://api.github.com/repos/locationtech/geogig/pulls/comments/96542023","pull_request_review_id":17125353,"id":96542023,"diff_hunk":"@@ -0,0 +1,125 @@\n+/*\n+ *  Copyright (c) 2017 Boundless and others.\n+ *  All rights reserved. This program and the accompanying materials\n+ *  are made available under the terms of the Eclipse Distribution License v1.0\n+ *  which accompanies this distribution, and is available at\n+ *  https://www.eclipse.org/org/documents/edl-v10.html\n+ *\n+ *  Contributors:\n+ *  Morgan Thompson (Boundless) - initial implementation\n+ *  Alex Goudine (Boundless)\n+ */\n+\n+package org.locationtech.geogig.data;\n+\n+import com.vividsolutions.jts.geom.Envelope;\n+import org.opengis.referencing.crs.CoordinateReferenceSystem;\n+import java.util.Collection;\n+import java.util.Set;\n+\n+import org.geotools.geometry.GeneralEnvelope;\n+import org.geotools.geometry.jts.ReferencedEnvelope;\n+import org.geotools.referencing.CRS;\n+import org.opengis.metadata.extent.Extent;\n+import org.opengis.metadata.extent.GeographicBoundingBox;\n+import org.opengis.metadata.extent.GeographicExtent;\n+import org.opengis.referencing.crs.CRSAuthorityFactory;\n+import org.opengis.referencing.operation.CoordinateOperation;\n+import org.opengis.referencing.operation.CoordinateOperationFactory;\n+\n+/**\n+ * Given a EPSG code, find the CRS bounds and return as an Envelope\n+ */\n+public class EPSGBoundsCalc {\n+\n+    /**\n+     * Get the bounds of the desired CRS, uses JTS ReferencedEnvelope transform to properly\n+     * handle polar projections\n+     * @param crs the target CoordinateReferenceSystem\n+     * @return bounds an Envelope containing the CRS bounds\n+     */\n+    public Envelope getExtents(CoordinateReferenceSystem crs) throws Exception {\n+\n+        final Extent domainOfValidity = crs.getDomainOfValidity();\n+\n+        if (null == domainOfValidity) {\n+            throw new Exception(\"No domain of validity provided by CRS definition\");\n+        }\n+\n+        Collection<? extends GeographicExtent> geographicElements;\n+        geographicElements = domainOfValidity.getGeographicElements();\n+\n+        if (null == geographicElements || geographicElements.size() != 1) {\n+            throw new Exception(\"Number of geographic elements != 1\");\n+        }\n+\n+        GeographicExtent geographicExtent = geographicElements.iterator().next();\n+        if (!(geographicExtent instanceof GeographicBoundingBox)) {\n+            throw new Exception(\"geographic extent is not a geographic bounding box\");\n+        }\n+\n+        if (!geographicExtent.getInclusion()) {\n+            throw new Exception(\"geographic extent is exclusive, can only deal with inclusive ones\");\n+        }\n+\n+        GeographicBoundingBox geographicBoundingBox = (GeographicBoundingBox) geographicExtent;\n+\n+        double minx = geographicBoundingBox.getWestBoundLongitude();\n+        double miny = geographicBoundingBox.getSouthBoundLatitude();\n+        double maxx = geographicBoundingBox.getEastBoundLongitude();\n+        double maxy = geographicBoundingBox.getNorthBoundLatitude();\n+\n+        CoordinateReferenceSystem wgs84LongFirst;\n+\n+        try {\n+\n+            wgs84LongFirst = CRS.decode(\"EPSG:4326\", true);\n+            CoordinateOperationFactory coordOpFactory = CRS.getCoordinateOperationFactory(true);\n+            CoordinateOperation op = coordOpFactory.createOperation(wgs84LongFirst,crs);\n+\n+            ReferencedEnvelope refEnvelope = new ReferencedEnvelope(minx, maxx, miny, maxy, wgs84LongFirst);\n+            GeneralEnvelope genEnvelope = CRS.transform(op, refEnvelope);\n+\n+            double xmax = genEnvelope.getMaximum(0);\n+            double ymax = genEnvelope.getMaximum(1);\n+            double xmin = genEnvelope.getMinimum(0);\n+            double ymin = genEnvelope.getMinimum(1);\n+\n+            Envelope envelope = new Envelope(xmin, xmax, ymin, ymax);\n+            return envelope;\n+        } catch (Exception e) {\n+            throw new Exception(\"ERROR: \" + e.getMessage());\n+        }\n+    }\n+\n+    /**\n+     * Search for the given CRS (EPSG code), return the bounds (domain of validity)\n+     * @param refId the input CRS\n+     * @return projectionBounds an Envelope describing the CRS bounds, or null if bounds are not found\n+     */\n+    public Envelope findCode(String refId) throws Exception {\n+        Envelope projectionBounds = null;\n+        CoordinateReferenceSystem crs = null;\n+\n+        CRSAuthorityFactory authorityFactory = CRS.getAuthorityFactory(true);\n+        Set<String> authorityCodes = authorityFactory.getAuthorityCodes(CoordinateReferenceSystem.class);\n+\n+        if (refId.contains(\"WGS 84\")) {\n+            crs = authorityFactory.createCoordinateReferenceSystem(\"EPSG:4326\");\n+            projectionBounds = getExtents(crs);","path":"src/core/src/main/java/org/locationtech/geogig/data/EPSGBoundsCalc.java","position":109,"original_position":109,"commit_id":"ef02abdf79b730531862de9162713419a436ff1c","original_commit_id":"ef02abdf79b730531862de9162713419a436ff1c","user":{"login":"DBlasby","id":14336967,"avatar_url":"https://avatars.githubusercontent.com/u/14336967?v=3","gravatar_id":"","url":"https://api.github.com/users/DBlasby","html_url":"https://github.com/DBlasby","followers_url":"https://api.github.com/users/DBlasby/followers","following_url":"https://api.github.com/users/DBlasby/following{/other_user}","gists_url":"https://api.github.com/users/DBlasby/gists{/gist_id}","starred_url":"https://api.github.com/users/DBlasby/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/DBlasby/subscriptions","organizations_url":"https://api.github.com/users/DBlasby/orgs","repos_url":"https://api.github.com/users/DBlasby/repos","events_url":"https://api.github.com/users/DBlasby/events{/privacy}","received_events_url":"https://api.github.com/users/DBlasby/received_events","type":"User","site_admin":false},"body":"Might want to just return the -180/-90 to 180/90 directly here - why are you special casing this?","created_at":"2017-01-18T00:09:50Z","updated_at":"2017-01-18T00:12:25Z","html_url":"https://github.com/locationtech/geogig/pull/224#discussion_r96542023","pull_request_url":"https://api.github.com/repos/locationtech/geogig/pulls/224","_links":{"self":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/comments/96542023"},"html":{"href":"https://github.com/locationtech/geogig/pull/224#discussion_r96542023"},"pull_request":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/224"}}},"pull_request":{"url":"https://api.github.com/repos/locationtech/geogig/pulls/224","id":101972195,"html_url":"https://github.com/locationtech/geogig/pull/224","diff_url":"https://github.com/locationtech/geogig/pull/224.diff","patch_url":"https://github.com/locationtech/geogig/pull/224.patch","issue_url":"https://api.github.com/repos/locationtech/geogig/issues/224","number":224,"state":"open","locked":false,"title":"Add CRS bounds calculator","user":{"login":"goudine","id":17364268,"avatar_url":"https://avatars.githubusercontent.com/u/17364268?v=3","gravatar_id":"","url":"https://api.github.com/users/goudine","html_url":"https://github.com/goudine","followers_url":"https://api.github.com/users/goudine/followers","following_url":"https://api.github.com/users/goudine/following{/other_user}","gists_url":"https://api.github.com/users/goudine/gists{/gist_id}","starred_url":"https://api.github.com/users/goudine/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/goudine/subscriptions","organizations_url":"https://api.github.com/users/goudine/orgs","repos_url":"https://api.github.com/users/goudine/repos","events_url":"https://api.github.com/users/goudine/events{/privacy}","received_events_url":"https://api.github.com/users/goudine/received_events","type":"User","site_admin":false},"body":"Added a CRS bounds calculator which returns the bounds of a valid CRS.\r\nReturns 'null' if the bounds cannot be retrieved.\r\nIncludes test cases verifying functionality.\r\n\r\nSigned-off-by: goudine <agoudine@boundlessgeo.com>","created_at":"2017-01-17T23:51:35Z","updated_at":"2017-01-18T00:12:25Z","closed_at":null,"merged_at":null,"merge_commit_sha":"002e91f9cd2164d9b7fb2ce5321fba470a090838","assignee":null,"assignees":[],"milestone":null,"commits_url":"https://api.github.com/repos/locationtech/geogig/pulls/224/commits","review_comments_url":"https://api.github.com/repos/locationtech/geogig/pulls/224/comments","review_comment_url":"https://api.github.com/repos/locationtech/geogig/pulls/comments{/number}","comments_url":"https://api.github.com/repos/locationtech/geogig/issues/224/comments","statuses_url":"https://api.github.com/repos/locationtech/geogig/statuses/ef02abdf79b730531862de9162713419a436ff1c","head":{"label":"goudine:CRSBoundsCalc","ref":"CRSBoundsCalc","sha":"ef02abdf79b730531862de9162713419a436ff1c","user":{"login":"goudine","id":17364268,"avatar_url":"https://avatars.githubusercontent.com/u/17364268?v=3","gravatar_id":"","url":"https://api.github.com/users/goudine","html_url":"https://github.com/goudine","followers_url":"https://api.github.com/users/goudine/followers","following_url":"https://api.github.com/users/goudine/following{/other_user}","gists_url":"https://api.github.com/users/goudine/gists{/gist_id}","starred_url":"https://api.github.com/users/goudine/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/goudine/subscriptions","organizations_url":"https://api.github.com/users/goudine/orgs","repos_url":"https://api.github.com/users/goudine/repos","events_url":"https://api.github.com/users/goudine/events{/privacy}","received_events_url":"https://api.github.com/users/goudine/received_events","type":"User","site_admin":false},"repo":{"id":71404318,"name":"geogig","full_name":"goudine/geogig","owner":{"login":"goudine","id":17364268,"avatar_url":"https://avatars.githubusercontent.com/u/17364268?v=3","gravatar_id":"","url":"https://api.github.com/users/goudine","html_url":"https://github.com/goudine","followers_url":"https://api.github.com/users/goudine/followers","following_url":"https://api.github.com/users/goudine/following{/other_user}","gists_url":"https://api.github.com/users/goudine/gists{/gist_id}","starred_url":"https://api.github.com/users/goudine/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/goudine/subscriptions","organizations_url":"https://api.github.com/users/goudine/orgs","repos_url":"https://api.github.com/users/goudine/repos","events_url":"https://api.github.com/users/goudine/events{/privacy}","received_events_url":"https://api.github.com/users/goudine/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/goudine/geogig","description":"GeoGig project","fork":true,"url":"https://api.github.com/repos/goudine/geogig","forks_url":"https://api.github.com/repos/goudine/geogig/forks","keys_url":"https://api.github.com/repos/goudine/geogig/keys{/key_id}","collaborators_url":"https://api.github.com/repos/goudine/geogig/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/goudine/geogig/teams","hooks_url":"https://api.github.com/repos/goudine/geogig/hooks","issue_events_url":"https://api.github.com/repos/goudine/geogig/issues/events{/number}","events_url":"https://api.github.com/repos/goudine/geogig/events","assignees_url":"https://api.github.com/repos/goudine/geogig/assignees{/user}","branches_url":"https://api.github.com/repos/goudine/geogig/branches{/branch}","tags_url":"https://api.github.com/repos/goudine/geogig/tags","blobs_url":"https://api.github.com/repos/goudine/geogig/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/goudine/geogig/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/goudine/geogig/git/refs{/sha}","trees_url":"https://api.github.com/repos/goudine/geogig/git/trees{/sha}","statuses_url":"https://api.github.com/repos/goudine/geogig/statuses/{sha}","languages_url":"https://api.github.com/repos/goudine/geogig/languages","stargazers_url":"https://api.github.com/repos/goudine/geogig/stargazers","contributors_url":"https://api.github.com/repos/goudine/geogig/contributors","subscribers_url":"https://api.github.com/repos/goudine/geogig/subscribers","subscription_url":"https://api.github.com/repos/goudine/geogig/subscription","commits_url":"https://api.github.com/repos/goudine/geogig/commits{/sha}","git_commits_url":"https://api.github.com/repos/goudine/geogig/git/commits{/sha}","comments_url":"https://api.github.com/repos/goudine/geogig/comments{/number}","issue_comment_url":"https://api.github.com/repos/goudine/geogig/issues/comments{/number}","contents_url":"https://api.github.com/repos/goudine/geogig/contents/{+path}","compare_url":"https://api.github.com/repos/goudine/geogig/compare/{base}...{head}","merges_url":"https://api.github.com/repos/goudine/geogig/merges","archive_url":"https://api.github.com/repos/goudine/geogig/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/goudine/geogig/downloads","issues_url":"https://api.github.com/repos/goudine/geogig/issues{/number}","pulls_url":"https://api.github.com/repos/goudine/geogig/pulls{/number}","milestones_url":"https://api.github.com/repos/goudine/geogig/milestones{/number}","notifications_url":"https://api.github.com/repos/goudine/geogig/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/goudine/geogig/labels{/name}","releases_url":"https://api.github.com/repos/goudine/geogig/releases{/id}","deployments_url":"https://api.github.com/repos/goudine/geogig/deployments","created_at":"2016-10-19T22:23:55Z","updated_at":"2016-10-19T22:23:59Z","pushed_at":"2017-01-17T23:49:50Z","git_url":"git://github.com/goudine/geogig.git","ssh_url":"git@github.com:goudine/geogig.git","clone_url":"https://github.com/goudine/geogig.git","svn_url":"https://github.com/goudine/geogig","homepage":null,"size":16897,"stargazers_count":0,"watchers_count":0,"language":"Java","has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":0,"forks":0,"open_issues":0,"watchers":0,"default_branch":"master"}},"base":{"label":"locationtech:master","ref":"master","sha":"a5331777768cb9dc3175003742f330a1a8b8dfe7","user":{"login":"locationtech","id":1991411,"avatar_url":"https://avatars.githubusercontent.com/u/1991411?v=3","gravatar_id":"","url":"https://api.github.com/users/locationtech","html_url":"https://github.com/locationtech","followers_url":"https://api.github.com/users/locationtech/followers","following_url":"https://api.github.com/users/locationtech/following{/other_user}","gists_url":"https://api.github.com/users/locationtech/gists{/gist_id}","starred_url":"https://api.github.com/users/locationtech/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/locationtech/subscriptions","organizations_url":"https://api.github.com/users/locationtech/orgs","repos_url":"https://api.github.com/users/locationtech/repos","events_url":"https://api.github.com/users/locationtech/events{/privacy}","received_events_url":"https://api.github.com/users/locationtech/received_events","type":"Organization","site_admin":false},"repo":{"id":21252787,"name":"geogig","full_name":"locationtech/geogig","owner":{"login":"locationtech","id":1991411,"avatar_url":"https://avatars.githubusercontent.com/u/1991411?v=3","gravatar_id":"","url":"https://api.github.com/users/locationtech","html_url":"https://github.com/locationtech","followers_url":"https://api.github.com/users/locationtech/followers","following_url":"https://api.github.com/users/locationtech/following{/other_user}","gists_url":"https://api.github.com/users/locationtech/gists{/gist_id}","starred_url":"https://api.github.com/users/locationtech/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/locationtech/subscriptions","organizations_url":"https://api.github.com/users/locationtech/orgs","repos_url":"https://api.github.com/users/locationtech/repos","events_url":"https://api.github.com/users/locationtech/events{/privacy}","received_events_url":"https://api.github.com/users/locationtech/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/locationtech/geogig","description":"GeoGig project","fork":false,"url":"https://api.github.com/repos/locationtech/geogig","forks_url":"https://api.github.com/repos/locationtech/geogig/forks","keys_url":"https://api.github.com/repos/locationtech/geogig/keys{/key_id}","collaborators_url":"https://api.github.com/repos/locationtech/geogig/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/locationtech/geogig/teams","hooks_url":"https://api.github.com/repos/locationtech/geogig/hooks","issue_events_url":"https://api.github.com/repos/locationtech/geogig/issues/events{/number}","events_url":"https://api.github.com/repos/locationtech/geogig/events","assignees_url":"https://api.github.com/repos/locationtech/geogig/assignees{/user}","branches_url":"https://api.github.com/repos/locationtech/geogig/branches{/branch}","tags_url":"https://api.github.com/repos/locationtech/geogig/tags","blobs_url":"https://api.github.com/repos/locationtech/geogig/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/locationtech/geogig/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/locationtech/geogig/git/refs{/sha}","trees_url":"https://api.github.com/repos/locationtech/geogig/git/trees{/sha}","statuses_url":"https://api.github.com/repos/locationtech/geogig/statuses/{sha}","languages_url":"https://api.github.com/repos/locationtech/geogig/languages","stargazers_url":"https://api.github.com/repos/locationtech/geogig/stargazers","contributors_url":"https://api.github.com/repos/locationtech/geogig/contributors","subscribers_url":"https://api.github.com/repos/locationtech/geogig/subscribers","subscription_url":"https://api.github.com/repos/locationtech/geogig/subscription","commits_url":"https://api.github.com/repos/locationtech/geogig/commits{/sha}","git_commits_url":"https://api.github.com/repos/locationtech/geogig/git/commits{/sha}","comments_url":"https://api.github.com/repos/locationtech/geogig/comments{/number}","issue_comment_url":"https://api.github.com/repos/locationtech/geogig/issues/comments{/number}","contents_url":"https://api.github.com/repos/locationtech/geogig/contents/{+path}","compare_url":"https://api.github.com/repos/locationtech/geogig/compare/{base}...{head}","merges_url":"https://api.github.com/repos/locationtech/geogig/merges","archive_url":"https://api.github.com/repos/locationtech/geogig/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/locationtech/geogig/downloads","issues_url":"https://api.github.com/repos/locationtech/geogig/issues{/number}","pulls_url":"https://api.github.com/repos/locationtech/geogig/pulls{/number}","milestones_url":"https://api.github.com/repos/locationtech/geogig/milestones{/number}","notifications_url":"https://api.github.com/repos/locationtech/geogig/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/locationtech/geogig/labels{/name}","releases_url":"https://api.github.com/repos/locationtech/geogig/releases{/id}","deployments_url":"https://api.github.com/repos/locationtech/geogig/deployments","created_at":"2014-06-26T19:45:58Z","updated_at":"2017-01-13T01:37:02Z","pushed_at":"2017-01-17T23:51:36Z","git_url":"git://github.com/locationtech/geogig.git","ssh_url":"git@github.com:locationtech/geogig.git","clone_url":"https://github.com/locationtech/geogig.git","svn_url":"https://github.com/locationtech/geogig","homepage":null,"size":17038,"stargazers_count":175,"watchers_count":175,"language":"Java","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":48,"mirror_url":null,"open_issues_count":13,"forks":48,"open_issues":13,"watchers":175,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/224"},"html":{"href":"https://github.com/locationtech/geogig/pull/224"},"issue":{"href":"https://api.github.com/repos/locationtech/geogig/issues/224"},"comments":{"href":"https://api.github.com/repos/locationtech/geogig/issues/224/comments"},"review_comments":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/224/comments"},"review_comment":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/locationtech/geogig/pulls/224/commits"},"statuses":{"href":"https://api.github.com/repos/locationtech/geogig/statuses/ef02abdf79b730531862de9162713419a436ff1c"}}}}
{"actor":{"display_login":"DBlasby"}}