Skip to content

Commit

Permalink
MONDRIAN-LAGUNITAS: Integrate from main.
Browse files Browse the repository at this point in the history
[git-p4: depot-paths = "//open/mondrian-release/lagunitas/": change = 14997]
  • Loading branch information
julianhyde committed Mar 12, 2012
1 parent c51b46e commit 61778c6
Show file tree
Hide file tree
Showing 59 changed files with 1,471 additions and 437 deletions.
6 changes: 3 additions & 3 deletions build.properties
Expand Up @@ -24,13 +24,13 @@ driver.version.major=4
driver.version.minor=0

#dependency for olap4j
dependency.olap4j-core.revision=1.0.1.494
dependency.olap4j.revision=1.0.1.494
dependency.olap4j-core.revision=1.0.1.500
dependency.olap4j.revision=1.0.1.500

#dependency properties: used during resolve step of workbench build
dependency.kettle.revision=TRUNK-SNAPSHOT
dependency.pentaho-xul.revision=TRUNK-SNAPSHOT
dependency.pentaho-launcher.revision=1.0.0
dependency.pentaho-launcher.revision=1.0.2

# Uncomment to use yDoc doclet for enhanced javadoc (requires commercial
# license).
Expand Down
1 change: 1 addition & 0 deletions intellij/mondrian.iml
Expand Up @@ -14,6 +14,7 @@
<orderEntry type="library" name="jdbcDrivers" level="project" />
<orderEntry type="library" name="pentaho" level="project" />
<orderEntry type="library" name="olap4j" level="project" />
<orderEntry type="library" name="validation-api" level="project" />
</component>
</module>

11 changes: 8 additions & 3 deletions intellij/mondrian.ipr
Expand Up @@ -43,8 +43,6 @@
<file url="file://$PROJECT_DIR$/../../olap4j/src/mondrian/olap4j/FactoryJdbc3Impl.java" />
<file url="file://$PROJECT_DIR$/../../olap4j/src/org/olap4j/driver/xmla/FactoryJdbc3Impl.java" />
<file url="file://$PROJECT_DIR$/../src/main/mondrian/olap4j/FactoryJdbc3Impl.java" />
<file url="file://$PROJECT_DIR$/../src/main/mondrian/rolap/RolapSchemaUpgrader.java" />
<file url="file://$PROJECT_DIR$/../src/main/mondrian/rolap/PhysSchemaConverter.java" />
</excludeFromCompile>
<resourceExtensions>
<entry name=".+\.(properties|xml|html|dtd|tld)" />
Expand Down Expand Up @@ -288,7 +286,7 @@
<component name="ProjectResources">
<default-html-doctype>http://www.w3.org/1999/xhtml</default-html-doctype>
</component>
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_5" assert-keyword="true" jdk-15="true" project-jdk-name="1.6" project-jdk-type="JavaSDK" />
<component name="ProjectRootManager" version="2" languageLevel="JDK_1_5" assert-keyword="true" jdk-15="true" project-jdk-name="1.7" project-jdk-type="JavaSDK" />
<component name="ResourceManagerContainer">
<option name="myResourceBundles">
<value>
Expand Down Expand Up @@ -436,6 +434,13 @@
<JAVADOC />
<SOURCES />
</library>
<library name="validation-api">
<CLASSES>
<root url="jar://$PROJECT_DIR$/../lib/validation-api.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES />
</library>
<library name="xmlunit">
<CLASSES>
<root url="jar://$PROJECT_DIR$/../lib/xmlunit.jar!/" />
Expand Down
4 changes: 4 additions & 0 deletions src/main/mondrian/olap/DrillThrough.java
Expand Up @@ -80,6 +80,10 @@ public int getMaxRowCount() {
public int getFirstRowOrdinal() {
return firstRowOrdinal;
}

public List<Exp> getReturnList() {
return returnList;
}
}

// End DrillThrough.java
18 changes: 14 additions & 4 deletions src/main/mondrian/olap4j/MondrianOlap4jCell.java
Expand Up @@ -9,6 +9,8 @@
*/
package mondrian.olap4j;

import mondrian.olap.Exp;
import mondrian.olap.Util;
import mondrian.rolap.RolapCell;
import mondrian.rolap.SqlStatement;

Expand All @@ -19,6 +21,7 @@

import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

/**
Expand Down Expand Up @@ -118,7 +121,13 @@ public String getFormattedValue() {
}

public ResultSet drillThrough() throws OlapException {
return drillThroughInternal(-1, -1, null, false, null, null);
return drillThroughInternal(
-1,
-1,
new ArrayList<Exp>(),
false,
null,
null);
}

/**
Expand All @@ -130,7 +139,8 @@ public ResultSet drillThrough() throws OlapException {
* @param maxRowCount Maximum number of rows to retrieve, <= 0 if unlimited
* @param firstRowOrdinal Ordinal of row to skip to (1-based), or 0 to
* start from beginning
* @param tabFields Comma-separated list of fields to return (deprecated)
* @param fields List of fields to return, expressed as MDX
* expressions.
* @param extendedContext If true, add non-constraining columns to the
* query for levels below each current member.
* This additional context makes the drill-through
Expand All @@ -143,7 +153,7 @@ public ResultSet drillThrough() throws OlapException {
ResultSet drillThroughInternal(
int maxRowCount,
int firstRowOrdinal,
String tabFields,
List<Exp> fields,
boolean extendedContext,
Logger logger,
int[] rowCountSlot)
Expand All @@ -157,7 +167,7 @@ ResultSet drillThroughInternal(
}
final SqlStatement sqlStmt =
cell.drillThroughInternal(
maxRowCount, firstRowOrdinal, tabFields, extendedContext,
maxRowCount, firstRowOrdinal, fields, extendedContext,
logger);
return sqlStmt.getWrappedResultSet();
}
Expand Down
2 changes: 1 addition & 1 deletion src/main/mondrian/olap4j/MondrianOlap4jConnection.java
Expand Up @@ -128,7 +128,7 @@ abstract class MondrianOlap4jConnection implements OlapConnection {
"does not start with '" + CONNECT_STRING_PREFIX + "'");
}
Util.PropertyList list = Util.parseConnectString(x);
final Map<String, String> map = Olap4jUtil.toMap(info);
final Map<String, String> map = Util.toMap(info);
for (Map.Entry<String, String> entry : map.entrySet()) {
list.put(entry.getKey(), entry.getValue());
}
Expand Down
4 changes: 3 additions & 1 deletion src/main/mondrian/olap4j/MondrianOlap4jStatement.java
Expand Up @@ -16,6 +16,7 @@
import mondrian.util.Pair;

import org.olap4j.*;
import org.olap4j.layout.RectangularCellSetFormatter;
import org.olap4j.mdx.*;

import java.io.PrintWriter;
Expand Down Expand Up @@ -94,11 +95,12 @@ ResultSet executeQuery2(
cellSet.getAxes().size(), 0);
final MondrianOlap4jCell cell =
(MondrianOlap4jCell) cellSet.getCell(coords);

ResultSet resultSet =
cell.drillThroughInternal(
drillThrough.getMaxRowCount(),
drillThrough.getFirstRowOrdinal(),
null,
drillThrough.getReturnList(),
true,
null,
rowCountSlot);
Expand Down
2 changes: 1 addition & 1 deletion src/main/mondrian/parser/MdxParser.jj
Expand Up @@ -1210,7 +1210,7 @@ List<Exp> returnItemList() :
i = returnItem() {
list.add(i);
}
)
)*
{
return list;
}
Expand Down
12 changes: 12 additions & 0 deletions src/main/mondrian/resource/MondrianResource.xml
Expand Up @@ -332,6 +332,18 @@
<text>Unknown dimension ''{0}'' for calculated member ''{1}'' in cube ''{2}''</text>
</exception>

<exception id="40121" name="CalcMemberHasBothDimensionAndHierarchy">
<text>Cannot specify both a dimension and hierarchy for calculated member ''{0}'' in cube ''{1}''</text>
</exception>

<exception id="40122" name="CalcMemberHasUnknownParent">
<text>Cannot find a parent with name ''{0}'' for calculated member ''{1}'' in cube ''{2}''</text>
</exception>

<exception id="40123" name="CalcMemberHasDifferentParentAndHierarchy">
<text>The calculated member ''{0}'' in cube ''{1}'' is defined for hierarchy ''{2}'' but its parent member is not part of that hierarchy</text>
</exception>

<exception id="40130" name="CalcMemberNotUnique">
<text>Calculated member ''{0}'' already exists in cube ''{1}''</text>
</exception>
Expand Down
26 changes: 24 additions & 2 deletions src/main/mondrian/rolap/CacheControlImpl.java
Expand Up @@ -228,7 +228,26 @@ protected void flushRegionList(List<CellRegion> cellRegionList) {
cellRegion = createUnionRegion(cellRegions);
break;
}
flush(cellRegion);
if (!containsMeasures(cellRegion)) {
for (RolapCube cube : connection.getSchema().getCubeList()) {
flush(
createCrossjoinRegion(
createMeasuresRegion(cube),
cellRegion));
}
} else {
flush(cellRegion);
}
}

private boolean containsMeasures(CellRegion cellRegion) {
final List<Hierarchy> hierarchyList = cellRegion.getDimensionality();
for (Hierarchy hierarchy : hierarchyList) {
if (hierarchy.getDimension().isMeasures()) {
return true;
}
}
return false;
}

public void trace(String message) {
Expand Down Expand Up @@ -1568,7 +1587,7 @@ public String toString() {
}

public void execute(final List<CellRegion> cellRegionList) {
// NOTE: use of member makes this class non-reentrant
// NOTE: use of cellRegionList makes this class non-reentrant
this.cellRegionList = cellRegionList;
set.accept(this);
this.cellRegionList = null;
Expand Down Expand Up @@ -1793,6 +1812,9 @@ public Boolean call() throws Exception {
* @param member Member
* @param parent Member's parent (generally equals member.getParentMember)
* @param cellRegionList List of cell regions to be flushed
*
* @return Callable that yields true when the member has been added to the
* cache
*/
private Callable<Boolean> addMember(
final RolapMember member,
Expand Down
21 changes: 20 additions & 1 deletion src/main/mondrian/rolap/FastBatchingCellReader.java
Expand Up @@ -21,6 +21,7 @@
import mondrian.util.*;

import org.apache.log4j.Logger;
import org.apache.log4j.MDC;

import java.util.*;
import java.util.concurrent.Future;
Expand Down Expand Up @@ -593,7 +594,15 @@ private void recordCellRequest2(final CellRequest request) {
// with the same target dimensionality. It is quite likely that the
// other rollup will satisfy this request, and it's complicated to be
// 100% sure. If we're wrong, we'll be back.
if (measure.getAggregator().getRollup().supportsFastAggregates(

// Also make sure that we don't try to rollup a measure which
// doesn't support rollup from raw data, like a distinct count
// for example. Both the measure's aggregator and its rollup
// aggregator must support raw data aggregation. We call
// Aggregator.supportsFastAggregates() to verify.
if (measure.getAggregator().supportsFastAggregates(
measure.getDatatype())
&& measure.getAggregator().getRollup().supportsFastAggregates(
measure.getDatatype())
&& !rollupBitmaps.contains(request.getConstrainedColumnsBitKey()))
{
Expand Down Expand Up @@ -792,6 +801,8 @@ public static class LoadBatchCommand
private final Dialect dialect;
private final RolapCube cube;
private final List<CellRequest> cellRequests;
private final Map<String, Object> mdc =
new HashMap<String, Object>();

public LoadBatchCommand(
Locus locus,
Expand All @@ -805,9 +816,17 @@ public LoadBatchCommand(
this.dialect = dialect;
this.cube = cube;
this.cellRequests = cellRequests;
if (MDC.getContext() != null) {
this.mdc.putAll(MDC.getContext());
}
}

public LoadBatchResponse call() {
if (MDC.getContext() != null) {
final Map<String, Object> old = MDC.getContext();
old.clear();
old.putAll(mdc);
}
return new BatchLoader(locus, cacheMgr, dialect, cube)
.load(cellRequests);
}
Expand Down
41 changes: 24 additions & 17 deletions src/main/mondrian/rolap/MemberCacheHelper.java
Expand Up @@ -4,13 +4,14 @@
// Agreement, available at the following URL:
// http://www.eclipse.org/legal/epl-v10.html.
// Copyright (C) 2001-2002 Kana Software, Inc.
// Copyright (C) 2001-2010 Julian Hyde and others
// Copyright (C) 2001-2012 Julian Hyde and others
// Copyright (C) 2004-2005 TONBELLER AG
// All Rights Reserved.
// You must accept the terms of that agreement to use this software.
*/
package mondrian.rolap;

import mondrian.olap.Level;
import mondrian.olap.Util;
import mondrian.rolap.cache.SmartCache;
import mondrian.rolap.cache.SoftSmartCache;
Expand Down Expand Up @@ -163,6 +164,10 @@ public synchronized void flushCache() {
mapMemberToChildren.clear();
mapKeyToMember.clear();
mapLevelToMembers.clear();
// We also need to clear the approxRowCount of each level.
for (Level level : rolapHierarchy.getLevels()) {
((RolapLevel)level).setApproxRowCount(Integer.MIN_VALUE);
}
}

public DataSourceChangeListener getChangeListener() {
Expand All @@ -180,27 +185,30 @@ public boolean isMutable()

public synchronized RolapMember removeMember(RolapLevel level, Object key)
{
// Flush entries from the level-to-members map
// for member's level and all child levels.
// Important: Do this even if the member is apparently not in the cache.
for (Iterator<Map.Entry<Pair<RolapLevel, Object>, List<RolapMember>>>
iterator = mapLevelToMembers.getCache().iterator();
iterator.hasNext();)
{
Map.Entry<Pair<RolapLevel, Object>, List<RolapMember>> entry =
iterator.next();
final RolapLevel cacheLevel = entry.getKey().left;
if (cacheLevel.equals(level)
|| (cacheLevel.getHierarchy().equals(level.getHierarchy())
&& cacheLevel.getDepth() >= level.getDepth()))
{
iterator.remove();
}
}

RolapMember member = getMember(level, key);
if (member == null) {
// not in cache
return null;
}

// Drop member from the level-to-members map.
// Cache key is a (level, constraint) pair,
// cache value is a list of RolapMember.
// For each cache key whose level matches, remove from the list,
// regardless of the constraint.
for (Map.Entry<Pair<RolapLevel, Object>, List<RolapMember>> entry
: mapLevelToMembers.getCache())
{
if (entry.getKey().left.equals(level)) {
List<RolapMember> peers = entry.getValue();
boolean removedIt = peers.remove(member);
Util.discard(removedIt);
}
}

// Drop member from the member-to-children map, wherever it occurs as
// a parent or as a child, regardless of the constraint.
RolapMember parent = member.getParentMember();
Expand Down Expand Up @@ -246,7 +254,6 @@ public RolapMember removeMemberAndDescendants(
// lists of children. Do need to update inferior lists of level-peers.
return null; // STUB
}

}

// End MemberCacheHelper.java
Expand Down

0 comments on commit 61778c6

Please sign in to comment.