This is an automated email from the ASF dual-hosted git repository.
reschke pushed a commit to branch master
in repository
https://gitbox.apache.org/repos/asf/sling-org-apache-sling-resourceresolver.git
The following commit(s) were added to refs/heads/master by this push:
new b3393d14 SLING-12832: alias refactoring - move alias init into
Runnable (#186)
b3393d14 is described below
commit b3393d1478e3965fcd85b434424bb2d181c38482
Author: Julian Reschke <[email protected]>
AuthorDate: Thu Jun 26 17:50:14 2025 +0200
SLING-12832: alias refactoring - move alias init into Runnable (#186)
---
.../impl/mapping/AliasHandler.java | 256 +++++++++++----------
1 file changed, 137 insertions(+), 119 deletions(-)
diff --git
a/src/main/java/org/apache/sling/resourceresolver/impl/mapping/AliasHandler.java
b/src/main/java/org/apache/sling/resourceresolver/impl/mapping/AliasHandler.java
index cf41d0ac..6b0e8d53 100644
---
a/src/main/java/org/apache/sling/resourceresolver/impl/mapping/AliasHandler.java
+++
b/src/main/java/org/apache/sling/resourceresolver/impl/mapping/AliasHandler.java
@@ -126,33 +126,10 @@ class AliasHandler {
return;
}
- List<String> conflictingAliases = new ArrayList<>();
- List<String> invalidAliases = new ArrayList<>();
-
// optimization made in SLING-2521
if (this.factory.isOptimizeAliasResolutionEnabled()) {
- try {
- this.aliasMapsMap = this.loadAliases(conflictingAliases,
invalidAliases);
-
- // warn if there are more than a few defunct aliases
- if (conflictingAliases.size() >=
MAX_REPORT_DEFUNCT_ALIASES) {
- log.warn(
- "There are {} conflicting aliases; excerpt:
{}",
- conflictingAliases.size(),
- conflictingAliases);
- } else if (!conflictingAliases.isEmpty()) {
- log.warn("There are {} conflicting aliases: {}",
conflictingAliases.size(), conflictingAliases);
- }
-
- if (invalidAliases.size() >= MAX_REPORT_DEFUNCT_ALIASES) {
- log.warn("There are {} invalid aliases; excerpt: {}",
invalidAliases.size(), invalidAliases);
- } else if (!invalidAliases.isEmpty()) {
- log.warn("There are {} invalid aliases: {}",
invalidAliases.size(), invalidAliases);
- }
- } catch (Exception e) {
- this.aliasMapsMap = UNITIALIZED_MAP;
- logDisableAliasOptimization(e);
- }
+ AliasInitializer ai = new AliasInitializer();
+ ai.run();
}
doUpdateConfiguration.run();
@@ -162,6 +139,141 @@ class AliasHandler {
}
}
+ private class AliasInitializer implements Runnable {
+
+ @Override
+ public void run() {
+ try {
+ execute();
+ } catch (Exception ex) {
+ log.error("alias initializer thread terminated with an
exception", ex);
+ }
+ }
+
+ private void execute() {
+ try {
+ List<String> conflictingAliases = new ArrayList<>();
+ List<String> invalidAliases = new ArrayList<>();
+
+ aliasMapsMap = loadAliases(conflictingAliases, invalidAliases);
+
+ // warn if there are more than a few defunct aliases
+ if (conflictingAliases.size() >= MAX_REPORT_DEFUNCT_ALIASES) {
+ log.warn(
+ "There are {} conflicting aliases; excerpt: {}",
+ conflictingAliases.size(),
+ conflictingAliases);
+ } else if (!conflictingAliases.isEmpty()) {
+ log.warn("There are {} conflicting aliases: {}",
conflictingAliases.size(), conflictingAliases);
+ }
+
+ if (invalidAliases.size() >= MAX_REPORT_DEFUNCT_ALIASES) {
+ log.warn("There are {} invalid aliases; excerpt: {}",
invalidAliases.size(), invalidAliases);
+ } else if (!invalidAliases.isEmpty()) {
+ log.warn("There are {} invalid aliases: {}",
invalidAliases.size(), invalidAliases);
+ }
+ } catch (Exception e) {
+ aliasMapsMap = UNITIALIZED_MAP;
+ logDisableAliasOptimization(e);
+ }
+ }
+
+ /**
+ * Load aliases - Search for all nodes (except under /jcr:system) below
+ * configured alias locations having the sling:alias property
+ */
+ @NotNull
+ private Map<String, Map<String, Collection<String>>> loadAliases(
+ @Nullable List<String> conflictingAliases, @Nullable
List<String> invalidAliases) {
+
+ Map<String, Map<String, Collection<String>>> map = new
ConcurrentHashMap<>();
+
+ try (ResourceResolver resolver =
+
factory.getServiceResourceResolver(factory.getServiceUserAuthenticationInfo(SERVICE_USER)))
{
+ String baseQueryString = generateAliasQuery();
+
+ Iterator<Resource> it;
+ try {
+ String queryStringWithSort =
+ baseQueryString + " AND FIRST([sling:alias]) >=
'%s' ORDER BY FIRST([sling:alias])";
+ it = new PagedQueryIterator("alias", "sling:alias",
resolver, queryStringWithSort, 2000);
+ } catch (QuerySyntaxException ex) {
+ log.debug("sort with first() not supported, falling back
to base query", ex);
+ it = queryUnpaged(baseQueryString, resolver);
+ } catch (UnsupportedOperationException ex) {
+ log.debug("query failed as unsupported, retrying without
paging/sorting", ex);
+ it = queryUnpaged(baseQueryString, resolver);
+ }
+
+ log.debug("alias initialization - start");
+ long count = 0;
+ long processStart = System.nanoTime();
+ while (it.hasNext()) {
+ count += 1;
+ loadAlias(it.next(), map, conflictingAliases,
invalidAliases);
+ }
+ long processElapsed = System.nanoTime() - processStart;
+ long resourcePerSecond =
+ (count * TimeUnit.SECONDS.toNanos(1) / (processElapsed
== 0 ? 1 : processElapsed));
+
+ String diagnostics = "";
+ if (it instanceof PagedQueryIterator) {
+ PagedQueryIterator pit = (PagedQueryIterator) it;
+
+ if (!pit.getWarning().isEmpty()) {
+ log.warn(pit.getWarning());
+ }
+
+ diagnostics = pit.getStatistics();
+ }
+
+ log.info(
+ "alias initialization - completed, processed {}
resources with sling:alias properties in {}ms (~{} resource/s){}",
+ count,
+ TimeUnit.NANOSECONDS.toMillis(processElapsed),
+ resourcePerSecond,
+ diagnostics);
+
+ aliasResourcesOnStartup.set(count);
+ } catch (LoginException ex) {
+ log.error("Alias init failed", ex);
+ }
+
+ return map;
+ }
+
+ /*
+ * generate alias query based on configured alias locations
+ */
+ @NotNull
+ private String generateAliasQuery() {
+ Set<String> allowedLocations = factory.getAllowedAliasLocations();
+
+ StringBuilder baseQuery = new StringBuilder("SELECT [sling:alias]
FROM [nt:base] WHERE ");
+
+ if (allowedLocations.isEmpty()) {
+ baseQuery.append(QueryBuildHelper.excludeSystemPath());
+ } else {
+ baseQuery.append(allowedLocations.stream()
+ .map(location -> "isdescendantnode('" +
QueryBuildHelper.escapeString(location) + "')")
+ .collect(Collectors.joining(" OR ", "(", ")")));
+ }
+
+ baseQuery.append(" AND [sling:alias] IS NOT NULL");
+ return baseQuery.toString();
+ }
+
+ @NotNull
+ private Iterator<Resource> queryUnpaged(@NotNull String query,
@NotNull ResourceResolver resolver) {
+ log.debug("start alias query: {}", query);
+ long queryStart = System.nanoTime();
+ Iterator<Resource> it = resolver.findResources(query, "JCR-SQL2");
+ long queryElapsed = System.nanoTime() - queryStart;
+ log.debug("end alias query; elapsed {}ms",
TimeUnit.NANOSECONDS.toMillis(queryElapsed));
+ return it;
+ }
+ }
+
boolean usesCache() {
return this.aliasMapsMap != UNITIALIZED_MAP;
}
@@ -378,90 +490,6 @@ class AliasHandler {
return result;
}
- /**
- * Load aliases - Search for all nodes (except under /jcr:system) below
- * configured alias locations having the sling:alias property
- */
- @NotNull
- private Map<String, Map<String, Collection<String>>> loadAliases(
- @Nullable List<String> conflictingAliases, @Nullable List<String>
invalidAliases) {
-
- Map<String, Map<String, Collection<String>>> map = new
ConcurrentHashMap<>();
-
- try (ResourceResolver resolver =
-
factory.getServiceResourceResolver(factory.getServiceUserAuthenticationInfo(SERVICE_USER)))
{
- String baseQueryString = generateAliasQuery();
-
- Iterator<Resource> it;
- try {
- String queryStringWithSort =
- baseQueryString + " AND FIRST([sling:alias]) >= '%s'
ORDER BY FIRST([sling:alias])";
- it = new PagedQueryIterator("alias", "sling:alias", resolver,
queryStringWithSort, 2000);
- } catch (QuerySyntaxException ex) {
- log.debug("sort with first() not supported, falling back to
base query", ex);
- it = queryUnpaged(baseQueryString, resolver);
- } catch (UnsupportedOperationException ex) {
- log.debug("query failed as unsupported, retrying without
paging/sorting", ex);
- it = queryUnpaged(baseQueryString, resolver);
- }
-
- log.debug("alias initialization - start");
- long count = 0;
- long processStart = System.nanoTime();
- while (it.hasNext()) {
- count += 1;
- loadAlias(it.next(), map, conflictingAliases, invalidAliases);
- }
- long processElapsed = System.nanoTime() - processStart;
- long resourcePerSecond = (count * TimeUnit.SECONDS.toNanos(1) /
(processElapsed == 0 ? 1 : processElapsed));
-
- String diagnostics = "";
- if (it instanceof PagedQueryIterator) {
- PagedQueryIterator pit = (PagedQueryIterator) it;
-
- if (!pit.getWarning().isEmpty()) {
- log.warn(pit.getWarning());
- }
-
- diagnostics = pit.getStatistics();
- }
-
- log.info(
- "alias initialization - completed, processed {} resources
with sling:alias properties in {}ms (~{} resource/s){}",
- count,
- TimeUnit.NANOSECONDS.toMillis(processElapsed),
- resourcePerSecond,
- diagnostics);
-
- this.aliasResourcesOnStartup.set(count);
- } catch (LoginException ex) {
- log.error("Alias init failed", ex);
- }
-
- return map;
- }
-
- /*
- * generate alias query based on configured alias locations
- */
- @NotNull
- private String generateAliasQuery() {
- Set<String> allowedLocations = this.factory.getAllowedAliasLocations();
-
- StringBuilder baseQuery = new StringBuilder("SELECT [sling:alias] FROM
[nt:base] WHERE ");
-
- if (allowedLocations.isEmpty()) {
- baseQuery.append(QueryBuildHelper.excludeSystemPath());
- } else {
- baseQuery.append(allowedLocations.stream()
- .map(location -> "isdescendantnode('" +
QueryBuildHelper.escapeString(location) + "')")
- .collect(Collectors.joining(" OR ", "(", ")")));
- }
-
- baseQuery.append(" AND [sling:alias] IS NOT NULL");
- return baseQuery.toString();
- }
-
/**
* Load alias given a resource
*/
@@ -593,16 +621,6 @@ class AliasHandler {
return invalid;
}
- @NotNull
- private Iterator<Resource> queryUnpaged(@NotNull String query, @NotNull
ResourceResolver resolver) {
- log.debug("start alias query: {}", query);
- long queryStart = System.nanoTime();
- Iterator<Resource> it = resolver.findResources(query, "JCR-SQL2");
- long queryElapsed = System.nanoTime() - queryStart;
- log.debug("end alias query; elapsed {}ms",
TimeUnit.NANOSECONDS.toMillis(queryElapsed));
- return it;
- }
-
private final AtomicLong lastTimeLogged = new AtomicLong(-1);
void logDisableAliasOptimization(@Nullable Exception e) {