Skip to content

Commit

Permalink
Initial import
Browse files Browse the repository at this point in the history
  • Loading branch information
phaneesh committed Apr 24, 2016
0 parents commit c2e697d
Show file tree
Hide file tree
Showing 12 changed files with 799 additions and 0 deletions.
14 changes: 14 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
/.idea/
target/
dist/
.idea
.idea_modules
atlassian-ide-plugin.xml
.DS_Store
log
logs
*.log
*.iml
*.ipr
*.iws

3 changes: 3 additions & 0 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
language: java
jdk:
- oraclejdk8
106 changes: 106 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
# Dropwizard MaxMind Bundle [![Travis build status](https://travis-ci.org/phaneesh/dropwizard-maxmind-bundle.svg?branch=master)](https://travis-ci.org/phaneesh/dropwizard-maxmind-bundle)

This bundle adds MaxMind GeoIP2 support for dropwizard.
This bundle compiles only on Java 8.

## Dependencies
* Dropwizard 0.9.2
* [GeoIP2 Java API](https://github.com/maxmind/GeoIP2-java)

## Usage
The bundle adds MaxMind GeoIP2 support for which makes it easier for geo ip information that is required by location aware services.
The bundle works with the free light version of MaxMind GeoIP2 database as well.

### Build instructions
- Clone the source:

git clone github.com/phaneesh/dropwizard-maxmind-bundle

- Build

mvn install

### Maven Dependency
Use the following repository:
```xml
<repository>
<id>clojars</id>
<name>Clojars repository</name>
<url>https://clojars.org/repo</url>
</repository>
```
Use the following maven dependency:
```xml
<dependency>
<groupId>io.dropwizard.xml</groupId>
<artifactId>dropwizard-maxmind-bundle</artifactId>
<version>0.0.1</version>
</dependency>
```

### Using MaxMind bundle

#### Bootstrap
```
@Override
public void initialize(final Bootstrap...) {
bootstrap.addBundle(new MaxMindBundle() {
public MaxMindConfig getMaxMindConfig(T configuration) {
...
}
});
}
```

#### Headers stamped
* X-MAXMIND-REQUEST-COUNTRY
* X-MAXMIND-REQUEST-STATE
* X-MAXMIND-REQUEST-CITY
* X-MAXMIND-REQUEST-POSTAL-CODE
* X-MAXMIND-REQUEST-LATITUDE
* X-MAXMIND-REQUEST-LONGITUDE
* X-MAXMIND-REQUEST-LOCATION-ACCURACY
* X-MAXMIND-REQUEST-USER-TYPE
* X-MAXMIND-REQUEST-CONNECTION-TYPE
* X-MAXMIND-REQUEST-ISP
* X-MAXMIND-REQUEST-LEGAL-PROXY
* X-MAXMIND-REQUEST-ANONYMOUS-IP
* X-MAXMIND-REQUEST-ANONYMOUS-VPN
* X-MAXMIND-REQUEST-TOR-NODE

#### MaxMindContext in Resource
Use MaxMindInfo which is much more convinient if you want easier access to all the stamped headers in a simple object model
* Example

```
@Produces({ MediaType.APPLICATION_JSON })
@Consumes({ MediaType.APPLICATION_JSON })
@Path("/")
public class MaxMindResource {
@GET
public Response maxMindInfoApi(@MaxMindContext final MaxMindInfo maxMindInfo) {
// Do work and return something
return Response.status(OK).entity(maxMindInfo).build();
}
}
```


LICENSE
-------

Copyright 2016 Phaneesh Nagaraja <[email protected]>.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
88 changes: 88 additions & 0 deletions pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>io.dropwizard.maxmind</groupId>
<artifactId>dropwizard-maxmind-bundle</artifactId>
<version>0.0.1</version>
<packaging>jar</packaging>

<name>dropwizard-maxmind-bundle</name>
<url>https://github.com/phaneesh/mxl-bundle</url>

<distributionManagement>
<repository>
<id>clojars</id>
<name>Clojars repository</name>
<url>https://clojars.org/repo</url>
</repository>
</distributionManagement>

<scm>
<connection>scm:git:https://github.com/phaneesh/dropwizard-maxmind-bundle.git</connection>
<developerConnection>scm:git:https://github.com/phaneesh/dropwizard-maxmind-bundle.git</developerConnection>
<tag>HEAD</tag>
<url>https://github.com/phaneesh/xml-bundle</url>
</scm>

<licenses>
<license>
<name>The Apache Software License, Version 2.0</name>
<url>http://www.apache.org/licenses/LICENSE-2.0.txt</url>
<distribution>repo</distribution>
<comments>A business-friendly OSS license</comments>
</license>
</licenses>

<developers>
<developer>
<id>phaneesh</id>
<name>Phaneesh Nagaraja</name>
<email>[email protected]</email>
</developer>
</developers>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<dropwizard.version>0.9.2</dropwizard.version>
<geoip2.version>2.7.0</geoip2.version>
<lombok.version>1.16.6</lombok.version>
<junit.version>4.12</junit.version>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
</properties>

<repositories>
<repository>
<id>clojars</id>
<name>Clojars repository</name>
<url>https://clojars.org/repo</url>
</repository>
</repositories>

<dependencies>
<dependency>
<groupId>io.dropwizard</groupId>
<artifactId>dropwizard-core</artifactId>
<version>${dropwizard.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.maxmind.geoip2</groupId>
<artifactId>geoip2</artifactId>
<version>${geoip2.version}</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
</dependencies>
</project>
60 changes: 60 additions & 0 deletions src/main/java/io/dropwizard/maxmind/geoip2/MaxMindBundle.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
/*
* Copyright 2016 Phaneesh Nagaraja <[email protected]>.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package io.dropwizard.maxmind.geoip2;

import io.dropwizard.Configuration;
import io.dropwizard.ConfiguredBundle;
import io.dropwizard.maxmind.geoip2.config.MaxMindConfig;
import io.dropwizard.maxmind.geoip2.filter.MaxMindGeoIpRequestFilter;
import io.dropwizard.maxmind.geoip2.provider.MaxMindContext;
import io.dropwizard.maxmind.geoip2.provider.MaxMindInfoProvider;
import io.dropwizard.setup.Bootstrap;
import io.dropwizard.setup.Environment;
import org.glassfish.hk2.api.InjectionResolver;
import org.glassfish.hk2.api.TypeLiteral;
import org.glassfish.hk2.utilities.binding.AbstractBinder;
import org.glassfish.jersey.server.spi.internal.ValueFactoryProvider;

import javax.inject.Singleton;

/**
* @author phaneesh
*/
public abstract class MaxMindBundle<T extends Configuration> implements ConfiguredBundle<T> {

public abstract MaxMindConfig getMaxMindConfig(final T configuration);

@Override
public void initialize(Bootstrap<?> bootstrap) {

}

@Override
public void run(final T configuration, final Environment environment) {
MaxMindConfig maxMindConfig = getMaxMindConfig(configuration);
environment.jersey().register(new MaxMindGeoIpRequestFilter(maxMindConfig));
if(maxMindConfig.isMaxMindContext()) {
environment.jersey().register(new AbstractBinder() {
@Override
protected void configure() {
bind(MaxMindInfoProvider.class).to(ValueFactoryProvider.class).in(Singleton.class);
bind(MaxMindInfoProvider.InjectResolver.class).to(
new TypeLiteral<InjectionResolver<MaxMindContext>>() {}).in(Singleton.class);
}
});
}
}
}
67 changes: 67 additions & 0 deletions src/main/java/io/dropwizard/maxmind/geoip2/cache/MaxMindCache.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
/*
* Copyright (c) 2016 Phaneesh Nagaraja <[email protected]>.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package io.dropwizard.maxmind.geoip2.cache;

import com.fasterxml.jackson.databind.JsonNode;
import com.google.common.cache.CacheBuilder;
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
import com.maxmind.db.NodeCache;
import io.dropwizard.maxmind.geoip2.config.MaxMindConfig;
import lombok.extern.slf4j.Slf4j;

import java.io.IOException;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;

/**
* @author phaneesh
*/
@Slf4j
public class MaxMindCache implements NodeCache {

private LoadingCache<Integer, JsonNode> cache;

private Loader loader;

public MaxMindCache(MaxMindConfig config) {
cache = CacheBuilder.newBuilder()
.expireAfterAccess(config.getCacheTTL(), TimeUnit.SECONDS)
.maximumSize(config.getCacheMaxEntries())
.recordStats()
.build(new CacheLoader<Integer, JsonNode>() {
@Override
public JsonNode load(Integer key) throws Exception {
return loader.load(key);
}
});
}

@Override
public JsonNode get(int i, Loader loader) throws IOException {
if(loader != null) {
this.loader = loader;
}
try {
return cache.get(i);
} catch (ExecutionException e) {
log.error("Error fetching info from cache", e);
return null;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
/*
* Copyright (c) 2016 Phaneesh Nagaraja <[email protected]>.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/
package io.dropwizard.maxmind.geoip2.config;

import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.hibernate.validator.constraints.NotEmpty;

/**
* @author phaneesh
*/
@Data
@AllArgsConstructor
@NoArgsConstructor
@Builder
public class MaxMindConfig {

@NotEmpty
private String databaseFilePath;

private String remoteIpHeader = "X-FORWARDED-FOR";

private int cacheTTL = 300;

private int cacheMaxEntries = 10000;

private boolean enterprise = false;

//country, city, anonymous
private String type;

private boolean maxMindContext = false;
}
Loading

0 comments on commit c2e697d

Please sign in to comment.