Skip to content

Commit 03d39e3

Browse files
committed
ExecTracker based on the dispatcher proposal from the Fuseki Mod PR #3184
1 parent 3f6987d commit 03d39e3

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

45 files changed

+3168
-20
lines changed

jena-arq/src/main/java/org/apache/jena/sparql/ARQConstants.java

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -326,6 +326,13 @@ public class ARQConstants
326326
public static final Symbol registryExtensions =
327327
SystemARQ.allocSymbol("registryExtensions") ;
328328

329-
public static void init() {}
329+
/** The query dispatcher registry key */
330+
public static final Symbol registryQueryDispachers =
331+
SystemARQ.allocSymbol("registryQueryDispachers") ;
332+
333+
/** The update dispatcher registry key */
334+
public static final Symbol registryUpdateDispatchers =
335+
SystemARQ.allocSymbol("registryUpdateDispatchers") ;
330336

337+
public static void init() {}
331338
}

jena-arq/src/main/java/org/apache/jena/sparql/engine/Timeouts.java

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -236,13 +236,23 @@ public static String toString(Timeout timeout) {
236236
return result;
237237
}
238238

239-
// Set times from context if not set directly. e..g Context provides default values.
240-
// Contrast with SPARQLQueryProcessor where the context is limiting values of the protocol parameter.
239+
/**
240+
* Update unset values in the builder with values from the context.
241+
*
242+
* Set times from context if not set directly, i.e. context provides default values.
243+
* Contrast with SPARQLQueryProcessor where the context is limiting values of the protocol parameter.
244+
*/
241245
public static void applyDefaultQueryTimeoutFromContext(TimeoutBuilderImpl builder, Context cxt) {
242246
Timeout queryTimeout = extractQueryTimeout(cxt);
243247
applyDefaultTimeout(builder, queryTimeout);
244248
}
245249

250+
/** Update unset values in the builder with values from the context. */
251+
public static void applyDefaultUpdateTimeoutFromContext(TimeoutBuilderImpl builder, Context cxt) {
252+
Timeout queryTimeout = extractUpdateTimeout(cxt);
253+
applyDefaultTimeout(builder, queryTimeout);
254+
}
255+
246256
/** Returns milliseconds if the given time unit is null. */
247257
private static TimeUnit nullToMillis(TimeUnit unit) {
248258
return unit != null ? unit : TimeUnit.MILLISECONDS;
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import org.apache.jena.query.Query;
25+
import org.apache.jena.sparql.core.DatasetGraph;
26+
import org.apache.jena.sparql.exec.QueryExec;
27+
import org.apache.jena.sparql.util.Context;
28+
29+
/**
30+
* A query dispatcher is responsible for taking a query and
31+
* preparing it for the execution against a dataset.
32+
* The result is a {@linkplain QueryExec} instance.
33+
*
34+
* Query dispatchers form a chain, and a {@link ChainingQueryDispatcher} acts as a link in such a chain.
35+
* A ChainingQueryDispatcher instance can choose to process a query by itself or to delegate processing to the
36+
* remainder of the chain.
37+
*
38+
* @see QueryDispatcherRegistry
39+
*/
40+
public interface ChainingQueryDispatcher {
41+
QueryExec create(Query query, DatasetGraph dsg, Context context, QueryDispatcher chain);
42+
}
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import org.apache.jena.sparql.core.DatasetGraph;
25+
import org.apache.jena.sparql.exec.UpdateExec;
26+
import org.apache.jena.sparql.util.Context;
27+
import org.apache.jena.update.UpdateRequest;
28+
29+
/**
30+
* An update dispatcher is responsible for taking an update request
31+
* preparing it for the execution against a dataset.
32+
* The result is a {@linkplain UpdateExec} instance.
33+
*
34+
* Update dispatchers form a chain, and a {@link ChainingUpdateDispatcher} acts as a link in such a chain.
35+
* A ChainingUpdateDispatcher instance can choose to process an update request by itself or to delegate processing to the
36+
* remainder of the chain.
37+
*
38+
* @see UpdateDispatcherRegistry
39+
*/
40+
public interface ChainingUpdateDispatcher {
41+
UpdateExec create(UpdateRequest updateRequest, DatasetGraph dsg, Context context, UpdateDispatcher chain);
42+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import org.apache.jena.query.Query;
25+
import org.apache.jena.sparql.core.DatasetGraph;
26+
import org.apache.jena.sparql.exec.QueryExec;
27+
import org.apache.jena.sparql.util.Context;
28+
29+
public interface QueryDispatcher {
30+
QueryExec create(Query query, DatasetGraph dsg, Context context);
31+
}
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import java.util.List;
25+
26+
import org.apache.jena.query.Query;
27+
import org.apache.jena.query.QueryException;
28+
import org.apache.jena.sparql.core.DatasetGraph;
29+
import org.apache.jena.sparql.exec.QueryExec;
30+
import org.apache.jena.sparql.util.Context;
31+
32+
/**
33+
* {@link QueryDispatcher} that invokes all dispatchers registered with {@link QueryDispatcherRegistry} in a chain.
34+
*/
35+
public class QueryDispatcherOverRegistry
36+
implements QueryDispatcher
37+
{
38+
protected QueryDispatcherRegistry registry;
39+
40+
/** Position in the chain */
41+
protected int pos;
42+
43+
public QueryDispatcherOverRegistry(QueryDispatcherRegistry registry) {
44+
this(registry, 0);
45+
}
46+
47+
public QueryDispatcherOverRegistry(QueryDispatcherRegistry registry, int pos) {
48+
super();
49+
this.registry = registry;
50+
this.pos = pos;
51+
}
52+
53+
protected ChainingQueryDispatcher getDispatcher() {
54+
List<ChainingQueryDispatcher> queryDispatchers = registry.dispatchers();
55+
int n = queryDispatchers.size();
56+
if (pos >= n) {
57+
throw new QueryException("No more elements in query dispatcher chain (pos=" + pos + ", chain size=" + n + ")");
58+
}
59+
ChainingQueryDispatcher dispatcher = queryDispatchers.get(pos);
60+
return dispatcher;
61+
}
62+
63+
@Override
64+
public QueryExec create(Query query, DatasetGraph dsg, Context context) {
65+
ChainingQueryDispatcher dispatcher = getDispatcher();
66+
QueryDispatcher next = new QueryDispatcherOverRegistry(registry, pos + 1);
67+
QueryExec result = dispatcher.create(query, dsg, context, next);
68+
return result;
69+
}
70+
}
Lines changed: 131 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,131 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import java.util.ArrayList;
25+
import java.util.Collections;
26+
import java.util.List;
27+
28+
import org.apache.jena.query.Query;
29+
import org.apache.jena.sparql.ARQConstants;
30+
import org.apache.jena.sparql.core.DatasetGraph;
31+
import org.apache.jena.sparql.exec.ChainingQueryDispatcherMain;
32+
import org.apache.jena.sparql.exec.QueryExec;
33+
import org.apache.jena.sparql.exec.QueryExecBuilder;
34+
import org.apache.jena.sparql.util.Context;
35+
36+
/**
37+
* Registry of {@link ChainingQueryDispatcher} instances.
38+
* Allows for plugging into the {@link QueryExecBuilder} creation process
39+
* based on dataset and context.
40+
*
41+
* @see ChainingQueryDispatcher
42+
* @since 6.1.0
43+
*/
44+
public class QueryDispatcherRegistry {
45+
List<ChainingQueryDispatcher> dispatchers = Collections.synchronizedList(new ArrayList<>());
46+
47+
// Singleton
48+
private static QueryDispatcherRegistry registry;
49+
static { init(); }
50+
51+
static public QueryDispatcherRegistry get() {
52+
return registry;
53+
}
54+
55+
/** If there is a QueryDispatcherRegistry in the context then return it otherwise yield the global instance */
56+
static public QueryDispatcherRegistry chooseRegistry(Context context) {
57+
QueryDispatcherRegistry result = get(context);
58+
if (result == null) {
59+
result = get();
60+
}
61+
return result;
62+
}
63+
64+
/** Get the QueryDispatcherRegistry from the context or null if there is none.
65+
* Returns null if the context is null. */
66+
static public QueryDispatcherRegistry get(Context context) {
67+
QueryDispatcherRegistry result = context == null
68+
? null
69+
: context.get(ARQConstants.registryQueryDispachers);
70+
return result;
71+
}
72+
73+
static public void set(Context context, QueryDispatcherRegistry registry) {
74+
context.set(ARQConstants.registryQueryDispachers, registry);
75+
}
76+
77+
public QueryDispatcherRegistry copy() {
78+
QueryDispatcherRegistry result = new QueryDispatcherRegistry();
79+
result.dispatchers.addAll(dispatchers);
80+
return result;
81+
}
82+
83+
/** Create a copy of the registry from the context or return a new instance */
84+
public static QueryDispatcherRegistry copyFrom(Context context) {
85+
QueryDispatcherRegistry tmp = get(context);
86+
QueryDispatcherRegistry result = tmp != null
87+
? tmp.copy()
88+
: new QueryDispatcherRegistry();
89+
return result;
90+
}
91+
92+
public QueryDispatcherRegistry() { }
93+
94+
private static void init() {
95+
registry = new QueryDispatcherRegistry();
96+
97+
registry.add(ChainingQueryDispatcherMain.get());
98+
}
99+
100+
// ----- Query -----
101+
102+
/** Add a ChainingQueryDispatcher to the default registry. */
103+
public static void addDispatcher(ChainingQueryDispatcher f) { get().add(f); }
104+
105+
/** Add a ChainingQueryDispatcher. */
106+
public void add(ChainingQueryDispatcher f) {
107+
// Add to low end so that newer factories are tried first
108+
dispatchers.add(0, f);
109+
}
110+
111+
/** Remove a ChainingQueryDispatcher from the default registry. */
112+
public static void removeDispatcher(ChainingQueryDispatcher f) { get().remove(f); }
113+
114+
/** Remove a ChainingQueryDispatcher. */
115+
public void remove(ChainingQueryDispatcher f) { dispatchers.remove(f); }
116+
117+
/** Allow <b>careful</b> manipulation of the dispatchers list */
118+
public List<ChainingQueryDispatcher> dispatchers() { return dispatchers; }
119+
120+
/** Check whether a ChainingQueryDispatcher is registered in the default registry. */
121+
public static boolean containsDispatcher(ChainingQueryDispatcher f) { return get().contains(f); }
122+
123+
/** Check whether a ChainingQueryDispatcher is already registered. */
124+
public boolean contains(ChainingQueryDispatcher f) { return dispatchers.contains(f); }
125+
126+
public static QueryExec create(Query query, DatasetGraph dsg, Context context) {
127+
QueryDispatcher dispatcher = new QueryDispatcherOverRegistry(registry);
128+
QueryExec qe = dispatcher.create(query, dsg, context);
129+
return qe;
130+
}
131+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
/*
2+
* Licensed to the Apache Software Foundation (ASF) under one
3+
* or more contributor license agreements. See the NOTICE file
4+
* distributed with this work for additional information
5+
* regarding copyright ownership. The ASF licenses this file
6+
* to you under the Apache License, Version 2.0 (the
7+
* "License"); you may not use this file except in compliance
8+
* with the License. You may obtain a copy of the License at
9+
*
10+
* https://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*
19+
* SPDX-License-Identifier: Apache-2.0
20+
*/
21+
22+
package org.apache.jena.sparql.engine.dispatch;
23+
24+
import org.apache.jena.sparql.core.DatasetGraph;
25+
import org.apache.jena.sparql.exec.UpdateExec;
26+
import org.apache.jena.sparql.util.Context;
27+
import org.apache.jena.update.UpdateRequest;
28+
29+
public interface UpdateDispatcher {
30+
UpdateExec create(UpdateRequest updateRequest, DatasetGraph dsg, Context context);
31+
}

0 commit comments

Comments
 (0)