Skip to content

Commit

Permalink
MONDRIAN: Implement union roles, both as part of the schema (via the …
Browse files Browse the repository at this point in the history
…<Union> construct) and as part of the connect string.

[git-p4: depot-paths = "//open/mondrian/": change = 10245]
  • Loading branch information
julianhyde committed Dec 1, 2007
1 parent a82e29a commit cfc96bf
Show file tree
Hide file tree
Showing 27 changed files with 676 additions and 141 deletions.
23 changes: 18 additions & 5 deletions doc/configuration.html
Expand Up @@ -50,15 +50,15 @@ <h3>Contents</h3>
<h3>1. Properties<a name="Properties">&nbsp;</a></h3>

<p>Mondrian has a properties file to allow you to configure how it executes. The
mondrian.properties file is loaded when the executing Mondrian JAR detects it
<code>mondrian.properties</code> file is loaded when the executing Mondrian JAR detects it
needs properties, but can also be done explicitly in your code. It looks in
several places, in the following order:</p>
<ol>
<li>In the directory where you started your JVM (Current working directory for
JVM process, java.exe on Win32, java on *nix).</li>
JVM process, java.exe on Win32, java on UNIX/Linux).</li>
<li>If there isn't mondrian.properties under current working directory of JVM
process, Class MondrianProperties's classloader will try to locate
mondrian.properties in all of its classpaths. So you may put mondrian.properties
mondrian.properties in all of its classpaths. So you may put <code>mondrian.properties</code>
under <code>/WEB-INF/classes</code> when you pack Mondrian into a Java web application.
The demonstration web applications have this configuration.</li>
</ol>
Expand Down Expand Up @@ -1088,7 +1088,20 @@ <h3>Connect string properties<a name="Connect_string_properties">&nbsp;</a></h3>
<td>No</td>
<td><p>The name of the <a href="schema.html#Access_control">role</a> to adopt
for access-control purposes. If not specified, the connection uses a role
which has access to every object in the schema.</p></td>
which has access to every object in the schema.</p>
<p>This property can contain multiple role names separated by commas. If
so, queries in the connection execute with the sum of the privileges of
all of the rules; the effect is the same as running under a
<a href="schema.html#Union_roles">union role</a>, defined using the
<code>&lt;Union&gt;</code> element in the schema file.</p>
<p>If a role name contains a comma, escape the comma using an extra
comma. For example, a connection created with</p>
<blockquote>
<p><code>Role='Pacific region manager,Europe,, Middle East and
Africa manager'</code></p>
</blockquote>
<p>will execute with the combined privileges of the roles &quot;Pacific
region manager&quot;, and &quot;Europe, Middle East and Africa manager&quot;.</p></td>
</tr>
<tr>
<td>jdbc.*</td>
Expand Down Expand Up @@ -1300,7 +1313,7 @@ <h3>Out Of Memory<a name="Out_of_memory"></a></h3>

<hr noshade size="1"/>
<p>
Author: Julian Hyde; last modified April 2007.<br/>
Author: Julian Hyde; last modified November, 2007.<br/>
Version: $Id$
(<a href="http://p4web.eigenbase.org/open/mondrian/doc/configuration.html?ac=22">log</a>)<br/>
Copyright (C) 2006-2007 Julian Hyde
Expand Down
27 changes: 14 additions & 13 deletions doc/mdx.html
Expand Up @@ -23,7 +23,7 @@
########################
## What is MDX? #####
######################## -->
<h3>What is MDX?</h3>
<h3>What is MDX?<a name="What_is_MDX">&nbsp;</a></h3>

<p>MDX stands for 'multi-dimensional expressions'. It is the main query language implemented by Mondrian.</p>

Expand All @@ -33,7 +33,7 @@ <h3>What is MDX?</h3>
####################################
## What is the syntax of MDX? #####
#################################### -->
<h3>What is the syntax of MDX?</h3>
<h3>What is the syntax of MDX?<a name="What_is_the_syntax_of_MDX">&nbsp;</a></h3>

<p>A basic MDX query looks like this:</p>

Expand All @@ -51,20 +51,21 @@ <h3>What is the syntax of MDX?</h3>
###############################
## Mondrian-specific MDX #####
############################### -->
<h3>Mondrian-specific MDX</h3>
<h3>Mondrian-specific MDX<a name="Mondrian_specific_MDX">&nbsp;</a></h3>

<h1>StrToSet and StrToTuple</h1>
<h1>StrToSet and StrToTuple<a name="StrToSet_and_StrToTuple">&nbsp;</a></h1>

<p>The StrToSet() and StrToTuple() functions take an extra parameter.</p>
<p>The <code>StrToSet()</code> and <code>StrToTuple()</code> functions take an extra parameter.</p>

<h1>Parsing</h1>
<h1>Parsing<a name="Parsing">&nbsp;</a></h1>

<p>Parsing is case-sensitive.</p>

<h1>Parameters</h1>
<h1>Parameters<a name="Parameters">&nbsp;</a></h1>

<p>Pseudo-functions Param() and ParamRef() allow you to create parameterized MDX statements.</p>
<h4>Cast operator</h4>
<p>Pseudo-functions <code>Param()</code> and <code>ParamRef()</code> allow you to create parameterized MDX statements.</p>

<h4>Cast operator<a name="Cast_operator">&nbsp;</a></h4>
<p>The Cast operator converts scalar expressions to other types. The syntax is</p>
<blockquote>
<p><code>Cast(&lt;Expression&gt; AS &lt;Type&gt;)</code></p>
Expand All @@ -83,7 +84,7 @@ <h4>Cast operator</h4>
<p>returns the value of the <code>[Store Sqft]</code> property as an integer
value.</p>

<h3><code>IN</code> and <code>NOT IN</code></h3>
<h3><code>IN</code> and <code>NOT IN</code><a name="In">&nbsp;</a></h3>

<p><code>IN</code> and <code>NOT IN</code> are Mondrian-specific functions.
For example:</p>
Expand All @@ -97,7 +98,7 @@ <h3><code>IN</code> and <code>NOT IN</code></h3>
FROM [Sales]</code>
</blockquote>

<h3><code>MATCHES</code> and <code>NOT MATCHES</code></h3>
<h3><code>MATCHES</code> and <code>NOT MATCHES</code><a name="Matches">&nbsp;</a></h3>

<p><code>MATCHES</code> and <code>NOT MATCHES</code> are Mondrian-specific
functions which compare a string with a <A href="http://java.sun.com/j2se/1.4.2/docs/api/java/util/regex/Pattern.html">Java regular expression</A>.
Expand All @@ -113,7 +114,7 @@ <h3><code>MATCHES</code> and <code>NOT MATCHES</code></h3>
########################
## Comments #####
######################## -->
<h3>Comments</h3>
<h3>Comments<a name="Comments">&nbsp;</a></h3>

<p>MDX statements can contain comments. There are 3 syntactic forms for comments:</p>

Expand Down Expand Up @@ -142,7 +143,7 @@ <h3>Comments</h3>
########################
## Format Strings #####
######################## -->
<h3>Format Strings</h3>
<h3>Format Strings<a name="Format_strings">&nbsp;</a></h3>

<p>Every member has a FORMAT_STRING property, which affects how its raw value is rendered into text in the user interface. For example, the query</p>

Expand Down
71 changes: 55 additions & 16 deletions doc/schema.html
Expand Up @@ -32,7 +32,7 @@
<li><a href="#Cubes_and_dimensions">Logical model</a>
<ol>
<li><a href="#Cube">Cube</a></li>
<li><a href="#Measures">Measures</a>
<li><a href="#Measures">Measures</a></li>
<li><a href="#Dimensions,_Hierarchies,_Levels">Dimensions, Hierarchies, Levels</a></li>
<ol>
<li><a href="#Mapping_Hierarchies">Mapping dimensions and hierarchies onto tables</a></li>
Expand Down Expand Up @@ -83,10 +83,11 @@
</ol>
</li>
<li><a href="#I18n">Internationalization</a></li>
<li><a href="#Aggregate_tables">Aggregate tables</a> </li>
<li><a href="#Aggregate_tables">Aggregate tables</a></li>
<li><a href="#Access_control">Access-control</a>
<ol>
<li><a href="#Defining_roles">Defining a role</a></li>
<li><a href="#Union_roles">Union roles</a></li>
<li><a href="#Setting_a_connections_role">Setting a connection's role</a></li>
</ol>
</li>
Expand Down Expand Up @@ -267,7 +268,7 @@ <h1>3.2 Measures<a name="Measures">&nbsp;</a></h1>
Here, we have chosen to output unit sales with no decimal places (since it is an integer), and store sales
with two decimal places (since it is a currency value). The ',' and '.' symbols are locale-sensitive, so if
you were running in Italian, store sales might appear as "48.123,45". You can achieve even more wild effects
using <a href="#Format_strings">advanced format strings</a>.</p>
using <a href="mdx.html#Format_strings">advanced format strings</a>.</p>

<p>A measure can have a caption attribute to be returned by the
<code><a href="http://sourceforge.net/api/mondrian/olap/Member.html#getCaption%28%29">Member.getCaption()</a></code>
Expand Down Expand Up @@ -1434,8 +1435,7 @@ <h1>5.4 Calculated members<a name="Calculated_members">&nbsp;</a></h1>
&lt;/<a href="#XML_CalculatedMember">CalculatedMember</a>&gt;</code>
</blockquote>

<p>Note that the <code>&lt;<a href="#XML_CalculatedMemberProperty">CalculatedMemberProperty</a>
&gt;</code> (not <code>&lt;<a href="#XML_Property">Property</a>&gt;</code>) element corresponds
<p>Note that the <code>&lt;<a href="#XML_CalculatedMemberProperty">CalculatedMemberProperty</a>&gt;</code> (not <code>&lt;<a href="#XML_Property">Property</a>&gt;</code>) element corresponds
to the <code>FORMAT_STRING = '$#,###'</code> fragment of the MDX statement. You can define
other properties here too, but <code>FORMAT_STRING</code> is by far the most useful in practice.</p>

Expand All @@ -1451,7 +1451,8 @@ <h1>5.4 Calculated members<a name="Calculated_members">&nbsp;</a></h1>
'|($#,##0.00)|style=red', '|$#,##0.00|style=green')"/&gt;</code>
</blockquote>

<p>For more details about format strings, see the <a href="mdx.html#Format_strings">MDX specification</a>.</p>
<p>For more details about format strings, see the
<a href="mdx.html#Format_strings">MDX specification</a>.</p>

<p>One additional calculated member property that is worth mentioning is DATATYPE.
As with <a href="#Measures">measures</a>,
Expand All @@ -1472,8 +1473,7 @@ <h1>5.4 Calculated members<a name="Calculated_members">&nbsp;</a></h1>


<p>You can make a calculated member or a measure invisible. If you specify <code>visible="false"
</code> (the default is "true") in the <code>&lt;<a href="#XML_Measure">Measure</a>&gt; or &lt;
<a href="#XML_CalculatedMember">CalculatedMember</a>&gt;</code> element, user-interfaces such as
</code> (the default is "true") in the <code>&lt;<a href="#XML_Measure">Measure</a>&gt;</code> or <code>&lt;<a href="#XML_CalculatedMember">CalculatedMember</a>&gt;</code> element, user-interfaces such as
JPivot will notice this property and hide the member. This is useful if you want to perform
calculations in a number of steps, and hide intermediate steps from end-users. For example,
here only "Margin per Sqft" is visible, and its factors "Store Cost", "Margin" and "Store Sqft"
Expand Down Expand Up @@ -1732,7 +1732,7 @@ <h1>6.1 User-defined function<a name="User-defined_function">&nbsp;</a></h1>
<code>&lt;<a href="#XML_Schema">Schema</a>&gt;<br>
&nbsp; ...<br>
&nbsp;&nbsp;&lt;<a href="#XML_UserDefinedFunction">UserDefinedFunction</a>
name="PlusOne" class="com.acme.PlusOneUdf"&gt;<br>
name="PlusOne" class="com.acme.PlusOneUdf" /&gt;<br>
&lt;/<a href="#XML_Schema">Schema</a>&gt;</code>
</blockquote>

Expand Down Expand Up @@ -2565,11 +2565,40 @@ <h1>9.1 Defining a role<a name="Defining_roles">&nbsp;</a></h1>
its child, California, is visible), but no other nations, and not All
Stores
(because it is above the top level, <code>Store Country</code>).</p>

<!--
#########################################
## 9.2 Setting a connection's role #####
######################################### -->
<h1>9.2 Setting a connection's role<a name="Setting_a_connections_role">&nbsp;</a></h1>
#########################
## 9.2 Union roles #####
######################### -->
<h1>9.2. Union roles<a name="Union_roles">&nbsp;</a></h1>
<p>A union role combines several roles, and has the sum of their privileges.</p>
<p>A union role can see a particular schema object if one or more of its
constituent roles can see it. Similarly, the rollup policy of a union role with
respect to a particular hierarchy is the least restrictive of all of the roles'
rollup policies.</p>
<p>Here is an example showing the syntax of a union role.</p>

<blockquote>
<code>&lt;<a href="#XML_Role">Role</a> name=&quot;Coastal manager&quot;&gt;<br>
&nbsp; &lt;<a href="#XML_Union">Union</a>&gt;<br>
&nbsp;&nbsp;&nbsp; &lt;<a href="#XML_RoleUsage">RoleUsage</a> roleName=&quot;California
manager&quot; /&gt;<br>
&nbsp;&nbsp;&nbsp; &lt;<a href="#XML_RoleUsage">RoleUsage</a> roleName=&quot;Eastern
sales manager&quot; /&gt;<br>
&nbsp; &lt;/<a href="#XML_Union">Union</a>&gt;<br>
&lt;/<a href="#XML_Role">Role</a>&gt;</code></blockquote>

<p>The constituent roles &quot;California manager&quot; and &quot;Eastern sales manager&quot; may be
regular roles, user-defined roles or union roles, but they must be declared
earlier in the schema file. The &quot;Coastal manager&quot; role will be able to see any
member that or a &quot;California manager&quot; and &quot;Eastern sales manager&quot;. It will be
able to see all the cells at the intersection of these members, plus it will be
able to see cells that neither role can see: for example, if only &quot;California
manager&quot; can see <code>[USA].[CA].[Fresno]</code>, and only &quot;Eastern sales
manager&quot; see the <code>[Sales Target]</code> measure, then &quot;Coastal manager&quot;
will be able to see the sales target for Fresno, which neither of the
constituent roles have access to.</p>
<h1>9.3 Setting a connection's role<a name="Setting_a_connections_role">&nbsp;</a></h1>

<p>A role only has effect when it is associated with a connection. By
default,
Expand All @@ -2586,7 +2615,9 @@ <h1>9.2 Setting a connection's role<a name="Setting_a_connections_role">&nbsp;</

<ol>
<li><b>In the connect string</b>. If you specify the <code>Role</code>
keyword in the connect string, the connection will adopt that role. See
keyword in the connect string, the connection will adopt that role. You can
specify multiple role names separated by commas, and a union role will be
created; if a role name contains a comma, escape it with an extra comma. See
<a href="api/mondrian/olap/DriverManager.html"> class DriverManager</a>
for examples of connect string syntax.</li>
<li><b>Programmatically</b>. Once your application has established a
Expand Down Expand Up @@ -2751,6 +2782,14 @@ <h3>10. Appendix A: XML elements<a name="Appendix_A_XML_elements">&nbsp;</a></h3
<tr>
<td><code>&lt;<a href="xml_schema.html#MemberGrant" name="XML_MemberGrant">MemberGrant</a>&gt;</code></td>
<td>A set of rights to a member and its children.</td>
</tr>
<tr>
<td><code>&lt;<a href="xml_schema.html#Union" name="XML_Union">Union</a>&gt;</code></td>
<td>Definition of a set of rights as the union of a set of roles.</td>
</tr>
<tr>
<td><code>&lt;<a href="xml_schema.html#RoleUsage" name="XML_RoleUsage">RoleUsage</a>&gt;</code></td>
<td>A reference to a Role.</td>
</tr>
<tr>
<td colspan="2"><i><br>Extensions</i></td>
Expand Down Expand Up @@ -2808,8 +2847,8 @@ <h3>10. Appendix A: XML elements<a name="Appendix_A_XML_elements">&nbsp;</a></h3

<p>Author: Julian Hyde; last modified September 2007.<br/>
Version: $Id$
(<a href="http://p4web.eigenbase.org/open/mondrian/doc/schema.html?ac=22">logg</a>)<br/>
Copyright (C) 2001-2002 Kana Software, Inc.<br/>
(<a href="http://p4web.eigenbase.org/open/mondrian/doc/schema.html?ac=22">log</a>)<br/>
Copyright (C) 2001-2002 Kana Software, Inc..<br/>
Copyright (C) 2002-2007 Julian Hyde and others
</p>

Expand Down
27 changes: 16 additions & 11 deletions src/main/mondrian/mdx/ParameterExpr.java
Expand Up @@ -49,18 +49,19 @@ public Exp accept(Validator validator) {
// the other one. The registered one will be resolved after everything
// else in the query has been resolved.
String parameterName = parameter.getName();
Parameter p = validator.getQuery().getSchemaReader(false).getParameter(
parameterName);
final SchemaReader schemaReader =
validator.getQuery().getSchemaReader(false);
Parameter p = schemaReader.getParameter(parameterName);
if (p == null) {
this.parameter = validator.createOrLookupParam(
true,
parameter.getName(),
parameter.getType(),
parameter.getDefaultExp(),
parameter.getDescription());
}
else {
this.parameter = p;
this.parameter =
validator.createOrLookupParam(
true,
parameter.getName(),
parameter.getType(),
parameter.getDefaultExp(),
parameter.getDescription());
} else {
this.parameter = p;
}
return this;
}
Expand Down Expand Up @@ -164,13 +165,17 @@ public int hashCode() {

/**
* Returns whether the parameter can be modified.
*
* @return whether parameter can be modified
*/
public boolean isModifiable() {
return true;
}

/**
* Returns the parameter used by this expression.
*
* @return parameter used by this expression
*/
public Parameter getParameter() {
return parameter;
Expand Down
4 changes: 4 additions & 0 deletions src/main/mondrian/olap/DelegatingSchemaReader.java
Expand Up @@ -52,6 +52,10 @@ public Member getMemberParent(Member member) {
return schemaReader.getMemberParent(member);
}

public Member substitute(Member member) {
return schemaReader.substitute(member);
}

public Member[] getMemberChildren(Member member) {
return schemaReader.getMemberChildren(member);
}
Expand Down
24 changes: 20 additions & 4 deletions src/main/mondrian/olap/Mondrian.xml
Expand Up @@ -1496,9 +1496,6 @@ Revision is $Id$
</Element>





<Class class="Expression">
<Code>
public abstract String getExpression(SqlQuery query);
Expand Down Expand Up @@ -1627,6 +1624,7 @@ Revision is $Id$
</Doc>
<Attribute name="name" required="true"/>
<Array name="schemaGrants" type="SchemaGrant"/>
<Object name="union" type="Union" required="false" />
</Element>

<Class class="Grant">
Expand Down Expand Up @@ -1726,7 +1724,25 @@ Revision is $Id$
</Attribute>
</Element>

<!-- UserDefinedFunction ====================================================== -->
<!-- Union ============================================================ -->
<Element type="Union">
<Doc>
Body of a Role definition which defines a Role to be the union
of several Roles. The RoleUsage elements must refer to Roles that
have been declared earlier in this schema file.
</Doc>
<Array name="roleUsages" type="RoleUsage" required="true"/>
</Element>

<!-- RoleUsage ======================================================== -->
<Element type="RoleUsage">
<Doc>
Usage of a Role in a union Role.
</Doc>
<Attribute name="roleName" required="true"/>
</Element>

<!-- UserDefinedFunction ============================================== -->
<Element type="UserDefinedFunction">
<Doc>
A <code>UserDefinedFunction</code> is a function which
Expand Down

0 comments on commit cfc96bf

Please sign in to comment.