diff --git a/ebean-api/src/main/java/io/ebean/ProfileLocation.java b/ebean-api/src/main/java/io/ebean/ProfileLocation.java index 33584a0b3..605de580a 100644 --- a/ebean-api/src/main/java/io/ebean/ProfileLocation.java +++ b/ebean-api/src/main/java/io/ebean/ProfileLocation.java @@ -45,6 +45,14 @@ public interface ProfileLocation { */ String label(); + /** + * Return a hash of the location that intentionally excludes the line number. + *
+ * The hash is expected to be stable regardless of line number in the source file + * so that is identifies the class and method location over a long time. + */ + long hash(); + /** * Return the full location. */ diff --git a/ebean-api/src/main/java/io/ebean/meta/MetaTimedMetric.java b/ebean-api/src/main/java/io/ebean/meta/MetaTimedMetric.java index f95f3248d..dbd0f0a0e 100644 --- a/ebean-api/src/main/java/io/ebean/meta/MetaTimedMetric.java +++ b/ebean-api/src/main/java/io/ebean/meta/MetaTimedMetric.java @@ -6,6 +6,14 @@ package io.ebean.meta; */ public interface MetaTimedMetric extends MetaMetric { + /** + * Return the metric location hash if defined. + *
+ * This hash excludes line number with the intention of being stable over time
+ * as code changes move the source line (but the method is the same).
+ */
+ long locationHash();
+
/**
* Return the metric location if defined.
*/
diff --git a/ebean-api/src/main/java/io/ebean/meta/MetricData.java b/ebean-api/src/main/java/io/ebean/meta/MetricData.java
index d8f80a0a9..7f2eb38b6 100644
--- a/ebean-api/src/main/java/io/ebean/meta/MetricData.java
+++ b/ebean-api/src/main/java/io/ebean/meta/MetricData.java
@@ -14,6 +14,7 @@ public class MetricData {
private Long mean;
private Long max;
private Long total;
+ private long locHash;
public MetricData(String name) {
this.name = name;
@@ -38,6 +39,14 @@ public class MetricData {
this.sqlHash = sqlHash;
}
+ public void setLocHash(long locHash) {
+ this.locHash = locHash;
+ }
+
+ public long getLocHash() {
+ return locHash;
+ }
+
public String getLoc() {
return loc;
}
diff --git a/ebean-api/src/main/java/io/ebean/metric/TimedMetricStats.java b/ebean-api/src/main/java/io/ebean/metric/TimedMetricStats.java
index 3012e9e9f..8c88d839e 100644
--- a/ebean-api/src/main/java/io/ebean/metric/TimedMetricStats.java
+++ b/ebean-api/src/main/java/io/ebean/metric/TimedMetricStats.java
@@ -12,6 +12,11 @@ public interface TimedMetricStats extends MetaTimedMetric {
*/
void setLocation(String location);
+ /**
+ * Additionally set the location hash.
+ */
+ void setLocationHash(long locationHash);
+
/**
* Override the name based on profile location.
*/
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetrics.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetrics.java
index f31fa849c..968e96a98 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetrics.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetrics.java
@@ -134,6 +134,7 @@ class DumpMetrics {
String location = metric.location();
if (dumpLoc && location != null) {
sb.append("\n loc:").append(location);
+ sb.append("\n locHash:").append(metric.locationHash());
}
if (dumpSql) {
sb.append(" \n\n sql:").append(metric.sql()).append("\n\n");
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsData.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsData.java
index 4ac8859b6..07980228f 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsData.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsData.java
@@ -56,6 +56,7 @@ class DumpMetricsData {
final MetricData data = create(metric);
appendCounters(data, metric);
data.setLoc(metric.location());
+ data.setLocHash(metric.locationHash());
}
private void addCount(MetaCountMetric metric) {
@@ -71,6 +72,7 @@ class DumpMetricsData {
}
private void appendLocationAndSql(MetricData data, MetaQueryMetric metric) {
+ data.setLocHash(metric.locationHash());
data.setLoc(metric.location());
data.setSql(metric.sql());
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsJson.java b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsJson.java
index b0644ec9f..c116ebd26 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsJson.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/core/DumpMetricsJson.java
@@ -188,6 +188,7 @@ class DumpMetricsJson implements ServerMetricsAsJson {
metricStart(metric);
appendTiming(metric);
if (isIncludeDetail(metric)) {
+ keyVal("locHash", metric.locationHash());
appendExtra("loc", metric.location());
}
metricEnd();
@@ -198,6 +199,7 @@ class DumpMetricsJson implements ServerMetricsAsJson {
appendTiming(metric);
if (withHash) {
keyVal("sqlHash", metric.sqlHash());
+ keyVal("locHash", metric.locationHash());
}
if (isIncludeDetail(metric)) {
appendExtra("loc", metric.location());
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/BasicProfileLocation.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/BasicProfileLocation.java
index 507938a96..8e8a5ffc0 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/BasicProfileLocation.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/BasicProfileLocation.java
@@ -10,9 +10,11 @@ final class BasicProfileLocation implements ProfileLocation {
private final String fullLocation;
private final String location;
private final String label;
+ private final long hash;
BasicProfileLocation(String fullLocation) {
this.fullLocation = fullLocation;
+ this.hash = UtilLocation.hash(fullLocation);
this.location = shortDesc(fullLocation);
this.label = UtilLocation.label(location);
}
@@ -42,6 +44,11 @@ final class BasicProfileLocation implements ProfileLocation {
return location;
}
+ @Override
+ public long hash() {
+ return hash;
+ }
+
@Override
public String fullLocation() {
return fullLocation;
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DProfileLocation.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DProfileLocation.java
index c5ff7d3ac..9c6340ad4 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DProfileLocation.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DProfileLocation.java
@@ -8,17 +8,14 @@ import io.ebean.ProfileLocation;
class DProfileLocation implements ProfileLocation {
private static final String IO_EBEAN = "io.ebean";
-
private static final String UNKNOWN = "unknown";
private String fullLocation;
-
private String location;
-
private String label;
+ private long hash;
private final int lineNumber;
-
private int traceCount;
DProfileLocation() {
@@ -53,6 +50,7 @@ class DProfileLocation implements ProfileLocation {
label = UtilLocation.label(shortDesc);
location = shortDesc;
fullLocation = loc;
+ hash = UtilLocation.hash(loc);
initWith(label);
return true;
}
@@ -71,6 +69,11 @@ class DProfileLocation implements ProfileLocation {
return location;
}
+ @Override
+ public long hash() {
+ return hash;
+ }
+
@Override
public String fullLocation() {
return fullLocation;
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMeta.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMeta.java
index 5359d96ed..0354bbd0a 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMeta.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMeta.java
@@ -49,6 +49,10 @@ class DQueryPlanMeta {
return (profileLocation == null) ? null : profileLocation.location();
}
+ public long getLocationHash() {
+ return (profileLocation == null) ? 0 : profileLocation.hash();
+ }
+
public String getSql() {
return sql;
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMetric.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMetric.java
index fda1d4d9b..41a0658f4 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMetric.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DQueryPlanMetric.java
@@ -83,6 +83,11 @@ class DQueryPlanMetric implements QueryPlanMetric {
return meta.getLocation();
}
+ @Override
+ public long locationHash() {
+ return meta.getLocationHash();
+ }
+
@Override
public long count() {
return stats.count();
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DTimeMetricStats.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DTimeMetricStats.java
index 2207fef3d..82731dfd3 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/DTimeMetricStats.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/DTimeMetricStats.java
@@ -7,18 +7,15 @@ import io.ebean.metric.TimedMetricStats;
*/
class DTimeMetricStats implements TimedMetricStats {
- private String name;
-
private final boolean collected;
-
- private String location;
-
private final long count;
-
private final long total;
-
private final long max;
+ private String name;
+ private String location;
+ private long locationHash;
+
DTimeMetricStats(String name, boolean collected, long count, long total, long max) {
this.name = name;
this.collected = collected;
@@ -40,6 +37,7 @@ class DTimeMetricStats implements TimedMetricStats {
.append(" max:").append(max);
if (location != null) {
sb.append(" loc:").append(location);
+ sb.append(" locHash:").append(locationHash);
}
return sb.toString();
}
@@ -49,6 +47,11 @@ class DTimeMetricStats implements TimedMetricStats {
this.location = location;
}
+ @Override
+ public void setLocationHash(long locationHash) {
+ this.locationHash = locationHash;
+ }
+
@Override
public boolean initialCollection() {
return !collected;
@@ -69,6 +72,11 @@ class DTimeMetricStats implements TimedMetricStats {
return location;
}
+ @Override
+ public long locationHash() {
+ return locationHash;
+ }
+
/**
* Return the count of values collected.
*/
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/profile/UtilLocation.java b/ebean-core/src/main/java/io/ebeaninternal/server/profile/UtilLocation.java
index 7b70dfcb7..00b388bbd 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/profile/UtilLocation.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/profile/UtilLocation.java
@@ -1,7 +1,21 @@
package io.ebeaninternal.server.profile;
+import io.ebeaninternal.server.util.Checksum;
+
final class UtilLocation {
+ /**
+ * Return a hash of the full description excluding the source line number.
+ */
+ static long hash(String full) {
+ final int pos = full.lastIndexOf('(');
+ if (pos > -1) {
+ return Checksum.checksum(full.substring(0, pos));
+ } else {
+ return Checksum.checksum(full);
+ }
+ }
+
static String label(String shortDescription) {
int pos = shortDescription.indexOf("(");
if (pos == -1) {
@@ -21,5 +35,4 @@ final class UtilLocation {
}
return desc;
}
-
}
diff --git a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryPlan.java b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryPlan.java
index 796290808..770ac522d 100644
--- a/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryPlan.java
+++ b/ebean-core/src/main/java/io/ebeaninternal/server/query/CQueryPlan.java
@@ -54,46 +54,32 @@ public class CQueryPlan implements SpiQueryPlan {
static final String RESULT_SET_BASED_RAW_SQL = "--ResultSetBasedRawSql";
private final SpiEbeanServer server;
-
private final ProfileLocation profileLocation;
-
private final String location;
-
+ private final long locationHash;
private final String label;
-
private final String name;
-
private final CQueryPlanKey planKey;
-
private final boolean rawSql;
-
private final String sql;
private final long sqlHash;
-
private final String logWhereSql;
-
private final SqlTree sqlTree;
/**
* Encrypted properties required additional binding.
*/
private final STreeProperty[] encryptedProps;
-
private final CQueryPlanStats stats;
-
private final Class> beanType;
-
final DataTimeZone dataTimeZone;
-
private final int asOfTableCount;
/**
* Key used to identify the query plan in audit logging.
*/
private volatile String auditQueryHash;
-
private final Set