aboutsummaryrefslogtreecommitdiff
path: root/src/org/traccar/reports
diff options
context:
space:
mode:
authorPhilipp Prangenberg <philipp.prangenberg@derkurier.de>2016-12-05 12:03:08 +0100
committerPhilipp Prangenberg <philipp.prangenberg@derkurier.de>2016-12-05 12:03:08 +0100
commita21f436a58133f7da0cae06366d729665f3b8f9c (patch)
tree72ff1743d96f79e4a9d85b0d48715e5f9aa67cf9 /src/org/traccar/reports
parent960bf899414d89221e92138fdb98777c3f4f73ec (diff)
parent40607036c5aa6385a7ae3f3a283bf107238a5944 (diff)
downloadtrackermap-server-a21f436a58133f7da0cae06366d729665f3b8f9c.tar.gz
trackermap-server-a21f436a58133f7da0cae06366d729665f3b8f9c.tar.bz2
trackermap-server-a21f436a58133f7da0cae06366d729665f3b8f9c.zip
Merge remote-tracking branch 'upstream/master'
Diffstat (limited to 'src/org/traccar/reports')
-rw-r--r--src/org/traccar/reports/Events.java113
-rw-r--r--src/org/traccar/reports/ReportUtils.java41
-rw-r--r--src/org/traccar/reports/Route.java83
-rw-r--r--src/org/traccar/reports/Summary.java61
-rw-r--r--src/org/traccar/reports/Trips.java129
-rw-r--r--src/org/traccar/reports/model/BaseReport.java4
-rw-r--r--src/org/traccar/reports/model/DeviceReport.java49
-rw-r--r--src/org/traccar/reports/model/SummaryReport.java4
-rw-r--r--src/org/traccar/reports/model/TripReport.java48
9 files changed, 417 insertions, 115 deletions
diff --git a/src/org/traccar/reports/Events.java b/src/org/traccar/reports/Events.java
index ed7e9e411..33893aad0 100644
--- a/src/org/traccar/reports/Events.java
+++ b/src/org/traccar/reports/Events.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,47 +16,120 @@
*/
package org.traccar.reports;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
import java.sql.SQLException;
+import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
-import javax.json.Json;
-import javax.json.JsonArrayBuilder;
-
+import org.joda.time.DateTime;
+import org.jxls.area.Area;
+import org.jxls.builder.xls.XlsCommentAreaBuilder;
+import org.jxls.common.CellRef;
+import org.jxls.formula.StandardFormulaProcessor;
+import org.jxls.transform.Transformer;
+import org.jxls.transform.poi.PoiTransformer;
+import org.jxls.util.TransformerFactory;
import org.traccar.Context;
+import org.traccar.model.Device;
import org.traccar.model.Event;
-import org.traccar.web.CsvBuilder;
-import org.traccar.web.JsonConverter;
+import org.traccar.model.Geofence;
+import org.traccar.model.Group;
+import org.traccar.reports.model.DeviceReport;
public final class Events {
private Events() {
}
- public static String getJson(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ public static Collection<Event> getObjects(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
Collection<String> types, Date from, Date to) throws SQLException {
- JsonArrayBuilder json = Json.createArrayBuilder();
+ ArrayList<Event> result = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- for (String type : types) {
- for (Event event : Context.getDataManager().getEvents(deviceId, type, from, to)) {
- json.add(JsonConverter.objectToJson(event));
+ Collection<Event> events = Context.getDataManager().getEvents(deviceId, from, to);
+ boolean all = types.isEmpty() || types.contains(Event.ALL_EVENTS);
+ for (Event event : events) {
+ if (all || types.contains(event.getType())) {
+ long geofenceId = event.getGeofenceId();
+ if (geofenceId == 0 || Context.getGeofenceManager().checkGeofence(userId, geofenceId)) {
+ result.add(event);
+ }
}
}
}
- return json.build().toString();
+ return result;
}
- public static String getCsv(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
- Collection<String> types, Date from, Date to) throws SQLException {
- CsvBuilder csv = new CsvBuilder();
- csv.addHeaderLine(new Event());
+ public static void getExcel(OutputStream outputStream,
+ long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ Collection<String> types, DateTime from, DateTime to) throws SQLException, IOException {
+ ArrayList<DeviceReport> devicesEvents = new ArrayList<>();
+ ArrayList<String> sheetNames = new ArrayList<>();
+ HashMap<Long, String> geofenceNames = new HashMap<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- for (String type : types) {
- csv.addArray(Context.getDataManager().getEvents(deviceId, type, from, to));
+ Collection<Event> events = Context.getDataManager().getEvents(deviceId, from.toDate(), to.toDate());
+ boolean all = types.isEmpty() || types.contains(Event.ALL_EVENTS);
+ for (Iterator<Event> iterator = events.iterator(); iterator.hasNext();) {
+ Event event = iterator.next();
+ if (all || types.contains(event.getType())) {
+ long geofenceId = event.getGeofenceId();
+ if (geofenceId != 0) {
+ if (Context.getGeofenceManager().checkGeofence(userId, geofenceId)) {
+ Geofence geofence = Context.getGeofenceManager().getGeofence(geofenceId);
+ if (geofence != null) {
+ geofenceNames.put(geofenceId, geofence.getName());
+ }
+ } else {
+ iterator.remove();
+ }
+ }
+ } else {
+ iterator.remove();
+ }
+ }
+ DeviceReport deviceEvents = new DeviceReport();
+ Device device = Context.getIdentityManager().getDeviceById(deviceId);
+ deviceEvents.setDeviceName(device.getName());
+ sheetNames.add(deviceEvents.getDeviceName());
+ if (device.getGroupId() != 0) {
+ Group group = Context.getDeviceManager().getGroupById(device.getGroupId());
+ if (group != null) {
+ deviceEvents.setGroupName(group.getName());
+ }
+ }
+ deviceEvents.setObjects(events);
+ devicesEvents.add(deviceEvents);
+ }
+ String templatePath = Context.getConfig().getString("report.templatesPath",
+ "templates/export/");
+ try (InputStream inputStream = new FileInputStream(templatePath + "/events.xlsx")) {
+ org.jxls.common.Context jxlsContext = PoiTransformer.createInitialContext();
+ jxlsContext.putVar("devices", devicesEvents);
+ jxlsContext.putVar("sheetNames", sheetNames);
+ jxlsContext.putVar("geofenceNames", geofenceNames);
+ jxlsContext.putVar("from", from);
+ jxlsContext.putVar("to", to);
+ jxlsContext.putVar("distanceUnit", ReportUtils.getDistanceUnit(userId));
+ jxlsContext.putVar("speedUnit", ReportUtils.getSpeedUnit(userId));
+ jxlsContext.putVar("timezone", from.getZone());
+ jxlsContext.putVar("bracketsRegex", "[\\{\\}\"]");
+ Transformer transformer = TransformerFactory.createTransformer(inputStream, outputStream);
+ List<Area> xlsAreas = new XlsCommentAreaBuilder(transformer).build();
+ for (Area xlsArea : xlsAreas) {
+ xlsArea.applyAt(new CellRef(xlsArea.getStartCellRef().getCellName()), jxlsContext);
+ xlsArea.setFormulaProcessor(new StandardFormulaProcessor());
+ xlsArea.processFormulas();
}
+ transformer.deleteSheet(xlsAreas.get(0).getStartCellRef().getSheetName());
+ transformer.write();
}
- return csv.build();
}
}
diff --git a/src/org/traccar/reports/ReportUtils.java b/src/org/traccar/reports/ReportUtils.java
index 818920ad5..032925a4a 100644
--- a/src/org/traccar/reports/ReportUtils.java
+++ b/src/org/traccar/reports/ReportUtils.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,20 +16,36 @@
*/
package org.traccar.reports;
+import org.traccar.Context;
+import org.traccar.helper.Log;
+import org.traccar.model.Position;
+
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.ArrayList;
import java.util.Collection;
-import org.traccar.Context;
-import org.traccar.helper.Log;
-import org.traccar.model.Position;
-
public final class ReportUtils {
private ReportUtils() {
}
+ public static String getDistanceUnit(long userId) {
+ String unit = Context.getPermissionsManager().getUser(userId).getDistanceUnit();
+ if (unit == null) {
+ unit = Context.getPermissionsManager().getServer().getDistanceUnit();
+ }
+ return unit != null ? unit : "km";
+ }
+
+ public static String getSpeedUnit(long userId) {
+ String unit = Context.getPermissionsManager().getUser(userId).getSpeedUnit();
+ if (unit == null) {
+ unit = Context.getPermissionsManager().getServer().getSpeedUnit();
+ }
+ return unit != null ? unit : "kn";
+ }
+
public static Collection<Long> getDeviceList(Collection<Long> deviceIds, Collection<Long> groupIds) {
Collection<Long> result = new ArrayList<>();
result.addAll(deviceIds);
@@ -47,18 +63,15 @@ public final class ReportUtils {
double distance = 0.0;
double firstOdometer = 0.0;
double lastOdometer = 0.0;
- if (firstPosition.getAttributes().containsKey(Position.KEY_ODOMETER)) {
- firstOdometer = ((Number) firstPosition.getAttributes().get(Position.KEY_ODOMETER)).doubleValue();
- }
- if (lastPosition.getAttributes().containsKey(Position.KEY_ODOMETER)) {
- lastOdometer = ((Number) lastPosition.getAttributes().get(Position.KEY_ODOMETER)).doubleValue();
- }
+ firstOdometer = firstPosition.getDouble(Position.KEY_ODOMETER);
+ lastOdometer = lastPosition.getDouble(Position.KEY_ODOMETER);
+
if (useOdometer && (firstOdometer != 0.0 || lastOdometer != 0.0)) {
distance = lastOdometer - firstOdometer;
} else if (firstPosition.getAttributes().containsKey(Position.KEY_TOTAL_DISTANCE)
&& lastPosition.getAttributes().containsKey(Position.KEY_TOTAL_DISTANCE)) {
- distance = ((Number) lastPosition.getAttributes().get(Position.KEY_TOTAL_DISTANCE)).doubleValue()
- - ((Number) firstPosition.getAttributes().get(Position.KEY_TOTAL_DISTANCE)).doubleValue();
+ distance = lastPosition.getDouble(Position.KEY_TOTAL_DISTANCE)
+ - firstPosition.getDouble(Position.KEY_TOTAL_DISTANCE);
}
return distance;
}
diff --git a/src/org/traccar/reports/Route.java b/src/org/traccar/reports/Route.java
index 45b81cd8c..468771a48 100644
--- a/src/org/traccar/reports/Route.java
+++ b/src/org/traccar/reports/Route.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,43 +16,88 @@
*/
package org.traccar.reports;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
import java.sql.SQLException;
+import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
+import java.util.List;
-import javax.json.Json;
-import javax.json.JsonArrayBuilder;
-
+import org.joda.time.DateTime;
+import org.jxls.area.Area;
+import org.jxls.builder.xls.XlsCommentAreaBuilder;
+import org.jxls.common.CellRef;
+import org.jxls.formula.StandardFormulaProcessor;
+import org.jxls.transform.Transformer;
+import org.jxls.transform.poi.PoiTransformer;
+import org.jxls.util.TransformerFactory;
import org.traccar.Context;
+import org.traccar.model.Device;
+import org.traccar.model.Group;
import org.traccar.model.Position;
-import org.traccar.web.CsvBuilder;
-import org.traccar.web.JsonConverter;
+import org.traccar.reports.model.DeviceReport;
public final class Route {
private Route() {
}
- public static String getJson(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ public static Collection<Position> getObjects(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
Date from, Date to) throws SQLException {
- JsonArrayBuilder json = Json.createArrayBuilder();
+ ArrayList<Position> result = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- for (Position position : Context.getDataManager().getPositions(deviceId, from, to)) {
- json.add(JsonConverter.objectToJson(position));
- }
+ result.addAll(Context.getDataManager().getPositions(deviceId, from, to));
}
- return json.build().toString();
+ return result;
}
- public static String getCsv(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
- Date from, Date to) throws SQLException {
- CsvBuilder csv = new CsvBuilder();
- csv.addHeaderLine(new Position());
+ public static void getExcel(OutputStream outputStream,
+ long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ DateTime from, DateTime to) throws SQLException, IOException {
+ ArrayList<DeviceReport> devicesRoutes = new ArrayList<>();
+ ArrayList<String> sheetNames = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- csv.addArray(Context.getDataManager().getPositions(deviceId, from, to));
+ Collection<Position> positions = Context.getDataManager()
+ .getPositions(deviceId, from.toDate(), to.toDate());
+ DeviceReport deviceRoutes = new DeviceReport();
+ Device device = Context.getIdentityManager().getDeviceById(deviceId);
+ deviceRoutes.setDeviceName(device.getName());
+ sheetNames.add(deviceRoutes.getDeviceName());
+ if (device.getGroupId() != 0) {
+ Group group = Context.getDeviceManager().getGroupById(device.getGroupId());
+ if (group != null) {
+ deviceRoutes.setGroupName(group.getName());
+ }
+ }
+ deviceRoutes.setObjects(positions);
+ devicesRoutes.add(deviceRoutes);
+ }
+ String templatePath = Context.getConfig().getString("report.templatesPath",
+ "templates/export/");
+ try (InputStream inputStream = new FileInputStream(templatePath + "/route.xlsx")) {
+ org.jxls.common.Context jxlsContext = PoiTransformer.createInitialContext();
+ jxlsContext.putVar("devices", devicesRoutes);
+ jxlsContext.putVar("sheetNames", sheetNames);
+ jxlsContext.putVar("from", from);
+ jxlsContext.putVar("to", to);
+ jxlsContext.putVar("distanceUnit", ReportUtils.getDistanceUnit(userId));
+ jxlsContext.putVar("speedUnit", ReportUtils.getSpeedUnit(userId));
+ jxlsContext.putVar("timezone", from.getZone());
+ jxlsContext.putVar("bracketsRegex", "[\\{\\}\"]");
+ Transformer transformer = TransformerFactory.createTransformer(inputStream, outputStream);
+ List<Area> xlsAreas = new XlsCommentAreaBuilder(transformer).build();
+ for (Area xlsArea : xlsAreas) {
+ xlsArea.applyAt(new CellRef(xlsArea.getStartCellRef().getCellName()), jxlsContext);
+ xlsArea.setFormulaProcessor(new StandardFormulaProcessor());
+ xlsArea.processFormulas();
+ }
+ transformer.deleteSheet(xlsAreas.get(0).getStartCellRef().getSheetName());
+ transformer.write();
}
- return csv.build();
}
}
diff --git a/src/org/traccar/reports/Summary.java b/src/org/traccar/reports/Summary.java
index d4171f644..cacb4d1d6 100644
--- a/src/org/traccar/reports/Summary.java
+++ b/src/org/traccar/reports/Summary.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,18 +16,21 @@
*/
package org.traccar.reports;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
import java.sql.SQLException;
+import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
-import javax.json.Json;
-import javax.json.JsonArrayBuilder;
-
+import org.joda.time.DateTime;
+import org.jxls.transform.poi.PoiTransformer;
+import org.jxls.util.JxlsHelper;
import org.traccar.Context;
import org.traccar.model.Position;
import org.traccar.reports.model.SummaryReport;
-import org.traccar.web.CsvBuilder;
-import org.traccar.web.JsonConverter;
public final class Summary {
@@ -47,12 +50,8 @@ public final class Summary {
if (firstPosition == null) {
firstPosition = position;
}
- if (previousPosition != null
- && position.getAttributes().get(Position.KEY_IGNITION) != null
- && Boolean.parseBoolean(position.getAttributes().get(Position.KEY_IGNITION).toString())
- && previousPosition.getAttributes().get(Position.KEY_IGNITION) != null
- && Boolean.parseBoolean(previousPosition.getAttributes()
- .get(Position.KEY_IGNITION).toString())) {
+ if (previousPosition != null && position.getBoolean(Position.KEY_IGNITION)
+ && previousPosition.getBoolean(Position.KEY_IGNITION)) {
result.addEngineHours(position.getFixTime().getTime()
- previousPosition.getFixTime().getTime());
}
@@ -61,31 +60,39 @@ public final class Summary {
result.setMaxSpeed(position.getSpeed());
}
boolean ignoreOdometer = Context.getDeviceManager()
- .lookupConfigBoolean(deviceId, "report.ignoreOdometer", false);
+ .lookupAttributeBoolean(deviceId, "report.ignoreOdometer", false, true);
result.setDistance(ReportUtils.calculateDistance(firstPosition, previousPosition, !ignoreOdometer));
result.setAverageSpeed(speedSum / positions.size());
}
return result;
}
- public static String getJson(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
- Date from, Date to) throws SQLException {
- JsonArrayBuilder json = Json.createArrayBuilder();
+ public static Collection<SummaryReport> getObjects(long userId, Collection<Long> deviceIds,
+ Collection<Long> groupIds, Date from, Date to) throws SQLException {
+ ArrayList<SummaryReport> result = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- json.add(JsonConverter.objectToJson(calculateSummaryResult(deviceId, from, to)));
+ result.add(calculateSummaryResult(deviceId, from, to));
}
- return json.build().toString();
+ return result;
}
- public static String getCsv(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
- Date from, Date to) throws SQLException {
- CsvBuilder csv = new CsvBuilder();
- csv.addHeaderLine(new SummaryReport());
- for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
- Context.getPermissionsManager().checkDevice(userId, deviceId);
- csv.addLine(calculateSummaryResult(deviceId, from, to));
+ public static void getExcel(OutputStream outputStream,
+ long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ DateTime from, DateTime to) throws SQLException, IOException {
+ Collection<SummaryReport> summaries = getObjects(userId, deviceIds, groupIds, from.toDate(), to.toDate());
+ String templatePath = Context.getConfig().getString("report.templatesPath",
+ "templates/export/");
+ try (InputStream inputStream = new FileInputStream(templatePath + "/summary.xlsx")) {
+ org.jxls.common.Context jxlsContext = PoiTransformer.createInitialContext();
+ jxlsContext.putVar("summaries", summaries);
+ jxlsContext.putVar("from", from);
+ jxlsContext.putVar("to", to);
+ jxlsContext.putVar("distanceUnit", ReportUtils.getDistanceUnit(userId));
+ jxlsContext.putVar("speedUnit", ReportUtils.getSpeedUnit(userId));
+ jxlsContext.putVar("timezone", from.getZone());
+ JxlsHelper.getInstance().setUseFastFormulaProcessor(false)
+ .processTemplate(inputStream, outputStream, jxlsContext);
}
- return csv.build();
}
}
diff --git a/src/org/traccar/reports/Trips.java b/src/org/traccar/reports/Trips.java
index f0a10edbd..a52d48f16 100644
--- a/src/org/traccar/reports/Trips.java
+++ b/src/org/traccar/reports/Trips.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,26 +16,38 @@
*/
package org.traccar.reports;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
-
-import javax.json.Json;
-import javax.json.JsonArrayBuilder;
-
+import java.util.List;
+
+import org.joda.time.DateTime;
+import org.jxls.area.Area;
+import org.jxls.builder.xls.XlsCommentAreaBuilder;
+import org.jxls.common.CellRef;
+import org.jxls.formula.StandardFormulaProcessor;
+import org.jxls.transform.Transformer;
+import org.jxls.transform.poi.PoiTransformer;
+import org.jxls.util.TransformerFactory;
import org.traccar.Context;
+import org.traccar.model.Device;
+import org.traccar.model.Group;
import org.traccar.model.Position;
+import org.traccar.reports.model.DeviceReport;
import org.traccar.reports.model.TripReport;
-import org.traccar.web.CsvBuilder;
-import org.traccar.web.JsonConverter;
public final class Trips {
private Trips() {
}
- private static TripReport calculateTrip(ArrayList<Position> positions, int startIndex, int endIndex) {
+ private static TripReport calculateTrip(
+ ArrayList<Position> positions, int startIndex, int endIndex, boolean ignoreOdometer) {
Position startTrip = positions.get(startIndex);
Position endTrip = positions.get(endIndex);
@@ -50,18 +62,24 @@ public final class Trips {
}
TripReport trip = new TripReport();
+
long tripDuration = endTrip.getFixTime().getTime() - positions.get(startIndex).getFixTime().getTime();
long deviceId = startTrip.getDeviceId();
trip.setDeviceId(deviceId);
trip.setDeviceName(Context.getIdentityManager().getDeviceById(deviceId).getName());
+
trip.setStartPositionId(startTrip.getId());
+ trip.setStartLat(startTrip.getLatitude());
+ trip.setStartLon(startTrip.getLongitude());
trip.setStartTime(startTrip.getFixTime());
trip.setStartAddress(startTrip.getAddress());
+
trip.setEndPositionId(endTrip.getId());
+ trip.setEndLat(endTrip.getLatitude());
+ trip.setEndLon(endTrip.getLongitude());
trip.setEndTime(endTrip.getFixTime());
trip.setEndAddress(endTrip.getAddress());
- boolean ignoreOdometer = Context.getDeviceManager()
- .lookupConfigBoolean(deviceId, "report.ignoreOdometer", false);
+
trip.setDistance(ReportUtils.calculateDistance(startTrip, endTrip, !ignoreOdometer));
trip.setDuration(tripDuration);
trip.setAverageSpeed(speedSum / (endIndex - startIndex));
@@ -71,15 +89,14 @@ public final class Trips {
return trip;
}
- private static Collection<TripReport> detectTrips(long deviceId, Date from, Date to) throws SQLException {
- double speedThreshold = Context.getConfig().getDouble("event.motion.speedThreshold", 0.01);
- long minimalTripDuration = Context.getConfig().getLong("report.trip.minimalTripDuration", 300) * 1000;
- double minimalTripDistance = Context.getConfig().getLong("report.trip.minimalTripDistance", 500);
- long minimalParkingDuration = Context.getConfig().getLong("report.trip.minimalParkingDuration", 300) * 1000;
- boolean greedyParking = Context.getConfig().getBoolean("report.trip.greedyParking");
+ protected static Collection<TripReport> detectTrips(
+ double speedThreshold, double minimalTripDistance,
+ long minimalTripDuration, long minimalParkingDuration, boolean greedyParking, boolean ignoreOdometer,
+ Collection<Position> positionCollection) {
+
Collection<TripReport> result = new ArrayList<>();
- ArrayList<Position> positions = new ArrayList<>(Context.getDataManager().getPositions(deviceId, from, to));
+ ArrayList<Position> positions = new ArrayList<>(positionCollection);
if (positions != null && !positions.isEmpty()) {
int previousStartParkingIndex = 0;
int startParkingIndex = -1;
@@ -131,7 +148,8 @@ public final class Trips {
if ((parkingDuration >= minimalParkingDuration || isLast)
&& previousEndParkingIndex < startParkingIndex) {
if (!tripFiltered) {
- result.add(calculateTrip(positions, previousEndParkingIndex, startParkingIndex));
+ result.add(calculateTrip(
+ positions, previousEndParkingIndex, startParkingIndex, ignoreOdometer));
}
previousEndParkingIndex = endParkingIndex;
skipped = false;
@@ -142,29 +160,78 @@ public final class Trips {
}
}
}
+
return result;
}
- public static String getJson(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ private static Collection<TripReport> detectTrips(long deviceId, Date from, Date to) throws SQLException {
+ double speedThreshold = Context.getConfig().getDouble("event.motion.speedThreshold", 0.01);
+ long minimalTripDuration = Context.getConfig().getLong("report.trip.minimalTripDuration", 300) * 1000;
+ double minimalTripDistance = Context.getConfig().getLong("report.trip.minimalTripDistance", 500);
+ long minimalParkingDuration = Context.getConfig().getLong("report.trip.minimalParkingDuration", 300) * 1000;
+ boolean greedyParking = Context.getConfig().getBoolean("report.trip.greedyParking");
+
+ boolean ignoreOdometer = Context.getDeviceManager()
+ .lookupAttributeBoolean(deviceId, "report.ignoreOdometer", false, true);
+
+ return detectTrips(
+ speedThreshold, minimalTripDistance, minimalTripDuration,
+ minimalParkingDuration, greedyParking, ignoreOdometer,
+ Context.getDataManager().getPositions(deviceId, from, to));
+ }
+
+ public static Collection<TripReport> getObjects(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
Date from, Date to) throws SQLException {
- JsonArrayBuilder json = Json.createArrayBuilder();
+ ArrayList<TripReport> result = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- for (TripReport tripReport : detectTrips(deviceId, from, to)) {
- json.add(JsonConverter.objectToJson(tripReport));
- }
+ result.addAll(detectTrips(deviceId, from, to));
}
- return json.build().toString();
+ return result;
}
- public static String getCsv(long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
- Date from, Date to) throws SQLException {
- CsvBuilder csv = new CsvBuilder();
- csv.addHeaderLine(new TripReport());
+ public static void getExcel(OutputStream outputStream,
+ long userId, Collection<Long> deviceIds, Collection<Long> groupIds,
+ DateTime from, DateTime to) throws SQLException, IOException {
+ ArrayList<DeviceReport> devicesTrips = new ArrayList<>();
+ ArrayList<String> sheetNames = new ArrayList<>();
for (long deviceId: ReportUtils.getDeviceList(deviceIds, groupIds)) {
Context.getPermissionsManager().checkDevice(userId, deviceId);
- csv.addArray(detectTrips(deviceId, from, to));
+ Collection<TripReport> trips = detectTrips(deviceId, from.toDate(), to.toDate());
+ DeviceReport deviceTrips = new DeviceReport();
+ Device device = Context.getIdentityManager().getDeviceById(deviceId);
+ deviceTrips.setDeviceName(device.getName());
+ sheetNames.add(deviceTrips.getDeviceName());
+ if (device.getGroupId() != 0) {
+ Group group = Context.getDeviceManager().getGroupById(device.getGroupId());
+ if (group != null) {
+ deviceTrips.setGroupName(group.getName());
+ }
+ }
+ deviceTrips.setObjects(trips);
+ devicesTrips.add(deviceTrips);
+ }
+ String templatePath = Context.getConfig().getString("report.templatesPath",
+ "templates/export/");
+ try (InputStream inputStream = new FileInputStream(templatePath + "/trips.xlsx")) {
+ org.jxls.common.Context jxlsContext = PoiTransformer.createInitialContext();
+ jxlsContext.putVar("devices", devicesTrips);
+ jxlsContext.putVar("sheetNames", sheetNames);
+ jxlsContext.putVar("from", from);
+ jxlsContext.putVar("to", to);
+ jxlsContext.putVar("distanceUnit", ReportUtils.getDistanceUnit(userId));
+ jxlsContext.putVar("speedUnit", ReportUtils.getSpeedUnit(userId));
+ jxlsContext.putVar("timezone", from.getZone());
+ Transformer transformer = TransformerFactory.createTransformer(inputStream, outputStream);
+ List<Area> xlsAreas = new XlsCommentAreaBuilder(transformer).build();
+ for (Area xlsArea : xlsAreas) {
+ xlsArea.applyAt(new CellRef(xlsArea.getStartCellRef().getCellName()), jxlsContext);
+ xlsArea.setFormulaProcessor(new StandardFormulaProcessor());
+ xlsArea.processFormulas();
+ }
+ transformer.deleteSheet(xlsAreas.get(0).getStartCellRef().getSheetName());
+ transformer.write();
}
- return csv.build();
}
+
}
diff --git a/src/org/traccar/reports/model/BaseReport.java b/src/org/traccar/reports/model/BaseReport.java
index 246cdede0..c33b9a8dd 100644
--- a/src/org/traccar/reports/model/BaseReport.java
+++ b/src/org/traccar/reports/model/BaseReport.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
diff --git a/src/org/traccar/reports/model/DeviceReport.java b/src/org/traccar/reports/model/DeviceReport.java
new file mode 100644
index 000000000..58caa809b
--- /dev/null
+++ b/src/org/traccar/reports/model/DeviceReport.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * 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 org.traccar.reports.model;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+
+public class DeviceReport {
+
+ private String deviceName;
+ public String getDeviceName() {
+ return deviceName;
+ }
+ public void setDeviceName(String deviceName) {
+ this.deviceName = deviceName;
+ }
+
+ private String groupName = "";
+ public String getGroupName() {
+ return groupName;
+ }
+ public void setGroupName(String groupName) {
+ this.groupName = groupName;
+ }
+
+ private List<?> objects;
+ public Collection<?> getObjects() {
+ return objects;
+ }
+ public void setObjects(Collection<?> objects) {
+ this.objects = new ArrayList<>(objects);
+ }
+
+}
diff --git a/src/org/traccar/reports/model/SummaryReport.java b/src/org/traccar/reports/model/SummaryReport.java
index 1e6655904..2d650381d 100644
--- a/src/org/traccar/reports/model/SummaryReport.java
+++ b/src/org/traccar/reports/model/SummaryReport.java
@@ -1,6 +1,6 @@
/*
- * Copyright 2016 Anton Tananaev (anton.tananaev@gmail.com)
- * Copyright 2016 Andrey Kunitsyn (abyss@fox5.ru)
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
diff --git a/src/org/traccar/reports/model/TripReport.java b/src/org/traccar/reports/model/TripReport.java
index 3a77b02ca..b28793e44 100644
--- a/src/org/traccar/reports/model/TripReport.java
+++ b/src/org/traccar/reports/model/TripReport.java
@@ -1,3 +1,19 @@
+/*
+ * Copyright 2016 Anton Tananaev (anton@traccar.org)
+ * Copyright 2016 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * 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 org.traccar.reports.model;
import java.util.Date;
@@ -20,6 +36,38 @@ public class TripReport extends BaseReport {
this.endPositionId = endPositionId;
}
+ private double startLat;
+ public double getStartLat() {
+ return startLat;
+ }
+ public void setStartLat(double startLat) {
+ this.startLat = startLat;
+ }
+
+ private double startLon;
+ public double getStartLon() {
+ return startLon;
+ }
+ public void setStartLon(double startLon) {
+ this.startLon = startLon;
+ }
+
+ private double endLat;
+ public double getEndLat() {
+ return endLat;
+ }
+ public void setEndLat(double endLat) {
+ this.endLat = endLat;
+ }
+
+ private double endLon;
+ public double getEndLon() {
+ return endLon;
+ }
+ public void setEndLon(double endLon) {
+ this.endLon = endLon;
+ }
+
private Date startTime;
public Date getStartTime() {
if (startTime != null) {