Skip to content

Commit

Permalink
[#5996] Add Field.as(Name) and Table.as(Name), Table.as(Name, Name...)
Browse files Browse the repository at this point in the history
  • Loading branch information
lukaseder committed Mar 22, 2017
1 parent f2b239a commit 04af931
Show file tree
Hide file tree
Showing 49 changed files with 464 additions and 162 deletions.
50 changes: 41 additions & 9 deletions jOOQ-codegen/src/main/java/org/jooq/util/JavaGenerator.java
Expand Up @@ -3342,7 +3342,7 @@ protected void generateTable(TableDefinition table, JavaWriter out) {
if (scala) { if (scala) {
out.tab(1).javadoc("Create a <code>%s</code> table reference", table.getQualifiedOutputName()); out.tab(1).javadoc("Create a <code>%s</code> table reference", table.getQualifiedOutputName());
out.tab(1).println("def this() = {"); out.tab(1).println("def this() = {");
out.tab(2).println("this(\"%s\", null, null)", table.getOutputName()); out.tab(2).println("this(%s.name(\"%s\"), null, null)", DSL.class, table.getOutputName());
out.tab(1).println("}"); out.tab(1).println("}");
} }
else { else {
Expand All @@ -3357,14 +3357,19 @@ protected void generateTable(TableDefinition table, JavaWriter out) {
out.tab(1).println("private %s() {", className); out.tab(1).println("private %s() {", className);
} }


out.tab(2).println("this(\"%s\", null);", table.getOutputName()); out.tab(2).println("this(%s.name(\"%s\"), null);", DSL.class, table.getOutputName());
out.tab(1).println("}"); out.tab(1).println("}");
} }




if (scala) { if (scala) {
out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName()); out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName());
out.tab(1).println("def this(alias : %s) = {", String.class); out.tab(1).println("def this(alias : %s) = {", String.class);
out.tab(2).println("this(%s.name(alias), %s, null)", DSL.class, tableId);
out.tab(1).println("}");

out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName());
out.tab(1).println("def this(alias : %s) = {", Name.class);
out.tab(2).println("this(alias, %s, null)", tableId); out.tab(2).println("this(alias, %s, null)", tableId);
out.tab(1).println("}"); out.tab(1).println("}");
} }
Expand All @@ -3376,14 +3381,19 @@ protected void generateTable(TableDefinition table, JavaWriter out) {
else if (generateInstanceFields()) { else if (generateInstanceFields()) {
out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName()); out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName());
out.tab(1).println("public %s(%s alias) {", className, String.class); out.tab(1).println("public %s(%s alias) {", className, String.class);
out.tab(2).println("this(%s.name(alias), %s);", DSL.class, tableId);
out.tab(1).println("}");

out.tab(1).javadoc("Create an aliased <code>%s</code> table reference", table.getQualifiedOutputName());
out.tab(1).println("public %s(%s alias) {", className, Name.class);
out.tab(2).println("this(alias, %s);", tableId); out.tab(2).println("this(alias, %s);", tableId);
out.tab(1).println("}"); out.tab(1).println("}");
} }


out.println(); out.println();


if (scala) { if (scala) {
out.tab(1).println("private def this(alias : %s, aliased : %s[%s]) = {", String.class, Table.class, recordType); out.tab(1).println("private def this(alias : %s, aliased : %s[%s]) = {", Name.class, Table.class, recordType);
if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("this(alias, aliased, new %s[ %s[_] ](%s))", out.ref("scala.Array"), Field.class, table.getParameters().size()); out.tab(2).println("this(alias, aliased, new %s[ %s[_] ](%s))", out.ref("scala.Array"), Field.class, table.getParameters().size());
else else
Expand All @@ -3392,7 +3402,7 @@ else if (generateInstanceFields()) {
out.tab(1).println("}"); out.tab(1).println("}");
} }
else { else {
out.tab(1).println("private %s(%s alias, %s<%s> aliased) {", className, String.class, Table.class, recordType); out.tab(1).println("private %s(%s alias, %s<%s> aliased) {", className, Name.class, Table.class, recordType);
if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("this(alias, aliased, new %s[%s]);", Field.class, table.getParameters().size()); out.tab(2).println("this(alias, aliased, new %s[%s]);", Field.class, table.getParameters().size());
else else
Expand All @@ -3401,7 +3411,7 @@ else if (generateInstanceFields()) {
out.tab(1).println("}"); out.tab(1).println("}");


out.println(); out.println();
out.tab(1).println("private %s(%s alias, %s<%s> aliased, %s<?>[] parameters) {", className, String.class, Table.class, recordType, Field.class); out.tab(1).println("private %s(%s alias, %s<%s> aliased, %s<?>[] parameters) {", className, Name.class, Table.class, recordType, Field.class);
out.tab(2).println("super(alias, null, aliased, parameters, \"%s\");", escapeString(comment)); out.tab(2).println("super(alias, null, aliased, parameters, \"%s\");", escapeString(comment));
out.tab(1).println("}"); out.tab(1).println("}");
} }
Expand Down Expand Up @@ -3563,6 +3573,17 @@ else if (generateInstanceFields()) {
out.println(); out.println();
out.tab(1).println("override def as(alias : %s) : %s = {", String.class, className); out.tab(1).println("override def as(alias : %s) : %s = {", String.class, className);


if (table.isTableValuedFunction())
out.tab(2).println("new %s(%s.name(alias), this, parameters)", className, DSL.class);
else
out.tab(2).println("new %s(%s.name(alias), this)", className, DSL.class);

out.tab(1).println("}");


out.println();
out.tab(1).println("override def as(alias : %s) : %s = {", Name.class, className);

if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("new %s(alias, this, parameters)", className); out.tab(2).println("new %s(alias, this, parameters)", className);
else else
Expand All @@ -3577,6 +3598,17 @@ else if (generateInstanceFields()) {
out.tab(1).overrideInherit(); out.tab(1).overrideInherit();
out.tab(1).println("public %s as(%s alias) {", className, String.class); out.tab(1).println("public %s as(%s alias) {", className, String.class);


if (table.isTableValuedFunction())
out.tab(2).println("return new %s(%s.name(alias), this, parameters);", className, DSL.class);
else
out.tab(2).println("return new %s(%s.name(alias), this);", className, DSL.class);

out.tab(1).println("}");


out.tab(1).overrideInherit();
out.tab(1).println("public %s as(%s alias) {", className, Name.class);

if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("return new %s(alias, this, parameters);", className); out.tab(2).println("return new %s(alias, this, parameters);", className);
else else
Expand All @@ -3590,9 +3622,9 @@ else if (generateInstanceFields()) {
out.tab(1).println("override def rename(name : %s) : %s = {", String.class, className); out.tab(1).println("override def rename(name : %s) : %s = {", String.class, className);


if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("new %s(name, null, parameters)", className); out.tab(2).println("new %s(%s.name(name), null, parameters)", className, DSL.class);
else else
out.tab(2).println("new %s(name, null)", className); out.tab(2).println("new %s(%s.name(name), null)", className, DSL.class);


out.tab(1).println("}"); out.tab(1).println("}");
} }
Expand All @@ -3604,9 +3636,9 @@ else if (generateInstanceFields()) {
out.tab(1).println("public %s rename(%s name) {", className, String.class); out.tab(1).println("public %s rename(%s name) {", className, String.class);


if (table.isTableValuedFunction()) if (table.isTableValuedFunction())
out.tab(2).println("return new %s(name, null, parameters);", className); out.tab(2).println("return new %s(%s.name(name), null, parameters);", className, DSL.class);
else else
out.tab(2).println("return new %s(name, null);", className); out.tab(2).println("return new %s(%s.name(name), null);", className, DSL.class);


out.tab(1).println("}"); out.tab(1).println("}");
} }
Expand Down
17 changes: 17 additions & 0 deletions jOOQ/src/main/java/org/jooq/Field.java
Expand Up @@ -154,6 +154,23 @@ public interface Field<T> extends SelectField<T>, GroupField, FieldOrRow {
@Support @Support
Field<T> as(String alias); Field<T> as(String alias);


/**
* Create an alias for this field.
* <p>
* Note that the case-sensitivity of the returned field depends on
* {@link Settings#getRenderNameStyle()} and the {@link Name}. By default,
* field aliases are quoted, and thus case-sensitive - use
* {@link DSL#unquotedName(String...)} for case-insensitive aliases.
* <p>
* If the argument {@link Name#getName()} is qualified, then the
* {@link Name#last()} part will be used.
*
* @param alias The alias name
* @return The field alias
*/
@Support
Field<T> as(Name alias);

/** /**
* Create an alias for this field based on another field's name. * Create an alias for this field based on another field's name.
* <p> * <p>
Expand Down
117 changes: 115 additions & 2 deletions jOOQ/src/main/java/org/jooq/Table.java
Expand Up @@ -379,6 +379,119 @@ public interface Table<R extends Record> extends TableLike<R> {
Table<R> as(String alias, BiFunction<? super Field<?>, ? super Integer, ? extends String> aliasFunction); Table<R> as(String alias, BiFunction<? super Field<?>, ? super Integer, ? extends String> aliasFunction);




/**
* Create an alias for this table.
* <p>
* Note that the case-sensitivity of the returned table depends on
* {@link Settings#getRenderNameStyle()} and the {@link Name}. By default,
* table aliases are quoted, and thus case-sensitive - use
* {@link DSL#unquotedName(String...)} for case-insensitive aliases.
* <p>
* If the argument {@link Name#getName()} is qualified, then the
* {@link Name#last()} part will be used.
*
* @param alias The alias name
* @return The table alias
*/
@Support
Table<R> as(Name alias);

/**
* Create an alias for this table and its fields.
* <p>
* Note that the case-sensitivity of the returned table depends on
* {@link Settings#getRenderNameStyle()} and the {@link Name}. By default,
* table aliases are quoted, and thus case-sensitive - use
* {@link DSL#unquotedName(String...)} for case-insensitive aliases.
* <p>
* If the argument {@link Name#getName()} is qualified, then the
* {@link Name#last()} part will be used.
* <p>
* <h5>Derived column lists for table references</h5>
* <p>
* Note, not all databases support derived column lists for their table
* aliases. On the other hand, some databases do support derived column
* lists, but only for derived tables. jOOQ will try to turn table
* references into derived tables to make this syntax work. In other words,
* the following statements are equivalent: <code><pre>
* -- Using derived column lists to rename columns (e.g. Postgres)
* SELECT t.a, t.b
* FROM my_table t(a, b)
*
* -- Nesting table references within derived tables (e.g. SQL Server)
* SELECT t.a, t.b
* FROM (
* SELECT * FROM my_table
* ) t(a, b)
* </pre></code>
* <p>
* <h5>Derived column lists for derived tables</h5>
* <p>
* Other databases may not support derived column lists at all, but they do
* support common table expressions. The following statements are
* equivalent: <code><pre>
* -- Using derived column lists to rename columns (e.g. Postgres)
* SELECT t.a, t.b
* FROM (
* SELECT 1, 2
* ) AS t(a, b)
*
* -- Using UNION ALL to produce column names (e.g. MySQL)
* SELECT t.a, t.b
* FROM (
* SELECT null a, null b FROM DUAL WHERE 1 = 0
* UNION ALL
* SELECT 1, 2 FROM DUAL
* ) t
* </pre></code>
*
* @param alias The alias name
* @param fieldAliases The field aliases. Excess aliases are ignored,
* missing aliases will be substituted by this table's field
* names.
* @return The table alias
*/
@Support
Table<R> as(Name alias, Name... fieldAliases);


/**
* Create an alias for this table and its fields.
* <p>
* This works like {@link #as(Name, Name...)}, except that field aliases
* are provided by a function. This is useful, for instance, to prefix all
* columns with a common prefix:
* <p>
* <code><pre>
* MY_TABLE.as("t1", f -> "prefix_" + f.getName());
* </pre></code>
*
* @param alias The alias name
* @param aliasFunction The function providing field aliases.
* @return The table alias
*/
@Support
Table<R> as(Name alias, Function<? super Field<?>, ? extends Name> aliasFunction);

/**
* Create an alias for this table and its fields.
* <p>
* This works like {@link #as(Name, Name...)}, except that field aliases
* are provided by a function. This is useful, for instance, to prefix all
* columns with a common prefix:
* <p>
* <code><pre>
* MY_TABLE.as("t1", (f, i) -> "column" + i);
* </pre></code>
*
* @param alias The alias name
* @param aliasFunction The function providing field aliases.
* @return The table alias
*/
@Support
Table<R> as(Name alias, BiFunction<? super Field<?>, ? super Integer, ? extends Name> aliasFunction);


/** /**
* Create an alias for this table based on another table's name. * Create an alias for this table based on another table's name.
* <p> * <p>
Expand Down Expand Up @@ -411,7 +524,7 @@ public interface Table<R extends Record> extends TableLike<R> {
/** /**
* Create an alias for this table and its fields. * Create an alias for this table and its fields.
* <p> * <p>
* This works like {@link #as(String, String...)}, except that field aliases * This works like {@link #as(Table, Field...)}, except that field aliases
* are provided by a function. This is useful, for instance, to prefix all * are provided by a function. This is useful, for instance, to prefix all
* columns with a common prefix: * columns with a common prefix:
* <p> * <p>
Expand All @@ -429,7 +542,7 @@ public interface Table<R extends Record> extends TableLike<R> {
/** /**
* Create an alias for this table and its fields. * Create an alias for this table and its fields.
* <p> * <p>
* This works like {@link #as(String, String...)}, except that field aliases * This works like {@link #as(Table, Field...)}, except that field aliases
* are provided by a function. This is useful, for instance, to prefix all * are provided by a function. This is useful, for instance, to prefix all
* columns with a common prefix: * columns with a common prefix:
* <p> * <p>
Expand Down
34 changes: 19 additions & 15 deletions jOOQ/src/main/java/org/jooq/impl/AbstractField.java
Expand Up @@ -87,6 +87,7 @@
import org.jooq.DatePart; import org.jooq.DatePart;
import org.jooq.Field; import org.jooq.Field;
import org.jooq.LikeEscapeStep; import org.jooq.LikeEscapeStep;
import org.jooq.Name;
import org.jooq.QuantifiedSelect; import org.jooq.QuantifiedSelect;
import org.jooq.Record; import org.jooq.Record;
import org.jooq.Record1; import org.jooq.Record1;
Expand All @@ -109,16 +110,16 @@ abstract class AbstractField<T> extends AbstractQueryPart implements Field<T> {
private static final long serialVersionUID = 2884811923648354905L; private static final long serialVersionUID = 2884811923648354905L;
private static final Clause[] CLAUSES = { FIELD }; private static final Clause[] CLAUSES = { FIELD };


private final String name; private final Name name;
private final String comment; private final String comment;
private final DataType<T> dataType; private final DataType<T> dataType;


AbstractField(String name, DataType<T> type) { AbstractField(Name name, DataType<T> type) {
this(name, type, null, type.getBinding()); this(name, type, null, type.getBinding());
} }


@SuppressWarnings("unchecked") @SuppressWarnings("unchecked")
AbstractField(String name, DataType<T> type, String comment, Binding<?, T> binding) { AbstractField(Name name, DataType<T> type, String comment, Binding<?, T> binding) {
super(); super();


this.name = name; this.name = name;
Expand Down Expand Up @@ -182,12 +183,18 @@ public final Record1<T> from(Record record) {
// ------------------------------------------------------------------------ // ------------------------------------------------------------------------


@Override @Override
public Field<T> as(String alias) { public final Field<T> as(String alias) {
return as(DSL.name(alias));
}

@Override
public Field<T> as(Name alias) {
return new FieldAlias<T>(this, alias); return new FieldAlias<T>(this, alias);
} }


@Override @Override
public final Field<T> as(Field<?> otherField) { public final Field<T> as(Field<?> otherField) {
// [#5997] TODO Change this
return as(otherField.getName()); return as(otherField.getName());
} }


Expand All @@ -202,7 +209,7 @@ public final Field<T> as(Function<? super Field<T>, ? extends String> aliasFunct


@Override @Override
public final String getName() { public final String getName() {
return name; return StringUtils.defaultIfNull(name.last(), "");
} }


@Override @Override
Expand Down Expand Up @@ -2032,28 +2039,25 @@ public final Field<T> coalesce(Field<T> option, Field<?>... options) {


@Override @Override
public boolean equals(Object that) { public boolean equals(Object that) {
if (this == that) { if (this == that)
return true; return true;
}


// [#2144] Non-equality can be decided early, without executing the // [#2144] Non-equality can be decided early, without executing the
// rather expensive implementation of AbstractQueryPart.equals() // rather expensive implementation of AbstractQueryPart.equals()
if (that instanceof AbstractField) { if (that instanceof AbstractField)
if (StringUtils.equals(name, (((AbstractField<?>) that).name))) { if (StringUtils.equals(name.last(), (((AbstractField<?>) that).name.last())))
return super.equals(that); return super.equals(that);
} else

return false;
else
return false; return false;
}

return false;
} }


@Override @Override
public int hashCode() { public int hashCode() {


// [#1938] This is a much more efficient hashCode() implementation // [#1938] This is a much more efficient hashCode() implementation
// compared to that of standard QueryParts // compared to that of standard QueryParts
return name.hashCode(); return name.last().hashCode();
} }
} }
2 changes: 1 addition & 1 deletion jOOQ/src/main/java/org/jooq/impl/AbstractFunction.java
Expand Up @@ -55,7 +55,7 @@ abstract class AbstractFunction<T> extends AbstractField<T> {
private final Field<?>[] arguments; private final Field<?>[] arguments;


AbstractFunction(String name, DataType<T> type, Field<?>... arguments) { AbstractFunction(String name, DataType<T> type, Field<?>... arguments) {
super(name, type); super(DSL.name(name), type);


this.arguments = arguments; this.arguments = arguments;
} }
Expand Down

0 comments on commit 04af931

Please sign in to comment.