Skip to content

Commit

Permalink
Merge pull request #915 from mikependon/repodb-enhancements
Browse files Browse the repository at this point in the history
#899 - place all the QueryField objects back into the Core library.
  • Loading branch information
mikependon authored Sep 18, 2021
2 parents 66e071e + 27f2378 commit 095d02c
Show file tree
Hide file tree
Showing 10 changed files with 737 additions and 0 deletions.
177 changes: 177 additions & 0 deletions RepoDb.Core/RepoDb/Extensions/QueryFields/FunctionalQueryField.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,177 @@
using RepoDb.Enumerations;
using RepoDb.Interfaces;
using System;

namespace RepoDb.Extensions.QueryFields
{
/// <summary>
/// A dynamic functional-based <see cref="QueryField"/> object. This requires a properly constructed
/// formatted string (for a specific database function) in order to work properly.
/// </summary>
/// <example>
/// See sample code below that uses a TRIM function.
/// <code>
/// var where = new FunctionalQueryField("ColumnName", "Value", "TRIM({0})");
/// var result = connection.Query&lt;Entity&gt;(where);
/// </code>
/// </example>
public class FunctionalQueryField : QueryField, IEquatable<FunctionalQueryField>
{
private int? hashCode = null;

#region Constructors

/// <summary>
/// Creates a new instance of <see cref="FunctionalQueryField"/> object.
/// </summary>
/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
/// <param name="format">The properly constructed format of the target function to be used.</param>
public FunctionalQueryField(string fieldName,
object value,
string format)
: this(fieldName, Operation.Equal, value, format)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
/// <param name="format">The properly constructed format of the target function to be used.</param>
public FunctionalQueryField(Field field,
object value,
string format)
: this(field, Operation.Equal, value, format)
{ }

/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
/// <param name="format">The properly constructed format of the target function to be used.</param>
public FunctionalQueryField(string fieldName,
Operation operation,
object value,
string format)
: this(new Field(fieldName), operation, value, format)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
/// <param name="format">The properly constructed format of the target function to be used.</param>
public FunctionalQueryField(Field field,
Operation operation,
object value,
string format)
: base(field, operation, value)
{
Format = format;
}

#endregion

#region Properties

/// <summary>
/// Gets the properly constructed format of the target function.
/// </summary>
public string Format { get; }

#endregion

#region Methods

/// <summary>
/// Gets the string representations (column-value pairs) of the current <see cref="QueryField"/> object with the formatted-function transformations.
/// </summary>
/// <param name="index">The target index.</param>
/// <param name="dbSetting">The database setting currently in used.</param>
/// <returns>The string representations of the current <see cref="QueryField"/> object using the LOWER function.</returns>
public override string GetString(int index,
IDbSetting dbSetting) =>
base.GetString(index, Format, dbSetting);

#endregion

#region Equality and comparers

/// <summary>
/// Returns the hashcode for this <see cref="FunctionalQueryField"/>.
/// </summary>
/// <returns>The hashcode value.</returns>
public override int GetHashCode()
{
if (this.hashCode != null)
{
return this.hashCode.Value;
}

// FullName: This is to ensure that even the user has created an identical formatting
// on the derived class with the existing classes, the Type.FullName could still
// differentiate the instances
var hashCode = GetType().FullName.GetHashCode();

// Base
hashCode += base.GetHashCode();

// Format
if (Format != null)
{
hashCode += Format.GetHashCode();
}

// Return
return (this.hashCode = hashCode).Value;
}

/// <summary>
/// Compares the <see cref="FunctionalQueryField"/> object equality against the given target object.
/// </summary>
/// <param name="obj">The object to be compared to the current object.</param>
/// <returns>True if the instances are equals.</returns>
public override bool Equals(object obj)
{
if (obj is null) return false;

return obj.GetHashCode() == GetHashCode();
}

/// <summary>
/// Compares the <see cref="FunctionalQueryField"/> object equality against the given target object.
/// </summary>
/// <param name="other">The object to be compared to the current object.</param>
/// <returns>True if the instances are equal.</returns>
public bool Equals(FunctionalQueryField other)
{
if (other is null) return false;

return other.GetHashCode() == GetHashCode();
}

/// <summary>
/// Compares the equality of the two <see cref="FunctionalQueryField"/> objects.
/// </summary>
/// <param name="objA">The first <see cref="FunctionalQueryField"/> object.</param>
/// <param name="objB">The second <see cref="FunctionalQueryField"/> object.</param>
/// <returns>True if the instances are equal.</returns>
public static bool operator ==(FunctionalQueryField objA,
FunctionalQueryField objB)
{
if (objA is null)
{
return objB is null;
}
return objA.Equals(objB);
}

/// <summary>
/// Compares the inequality of the two <see cref="FunctionalQueryField"/> objects.
/// </summary>
/// <param name="objA">The first <see cref="FunctionalQueryField"/> object.</param>
/// <param name="objB">The second <see cref="FunctionalQueryField"/> object.</param>
/// <returns>True if the instances are not equal.</returns>
public static bool operator !=(FunctionalQueryField objA,
FunctionalQueryField objB) =>
(objA == objB) == false;

#endregion
}
}
107 changes: 107 additions & 0 deletions RepoDb.Core/RepoDb/Extensions/QueryFields/LeftQueryField.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
using RepoDb.Enumerations;

namespace RepoDb.Extensions.QueryFields
{
/// <summary>
/// A functional-based <see cref="QueryField"/> object that is using the LEFT function.
/// </summary>
public sealed class LeftQueryField : FunctionalQueryField
{
private int? hashCode = null;

#region Constructors

/// <summary>
/// Creates a new instance of <see cref="LeftQueryField"/> object.
/// </summary>
/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftQueryField(string fieldName,
string value)
: this(fieldName, Operation.Equal, value)
{ }

/// <summary>
/// Creates a new instance of <see cref="LeftQueryField"/> object.
/// </summary>
/// <param name="field">The actual field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftQueryField(Field field,
string value)
: this(field, Operation.Equal, value)
{ }

/// <summary>
/// Creates a new instance of <see cref="LeftQueryField"/> object.
/// </summary>
/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftQueryField(string fieldName,
Operation operation,
string value)
: this(new Field(fieldName), operation, value)
{ }

/// <summary>
/// Creates a new instance of <see cref="LeftQueryField"/> object.
/// </summary>
/// <param name="field">The actual field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftQueryField(Field field,
Operation operation,
string value)
: this(field, operation, value, (value?.Length).GetValueOrDefault())
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
/// <param name="charCount">The number of characters from the left to be evaluated.</param>
private LeftQueryField(Field field,
Operation operation,
string value,
int charCount)
: base(field, operation, value, $"LEFT({{0}}, {charCount})")
{
CharCount = charCount;
}

#endregion

#region Properties

/// <summary>
/// Gets the value that defines the number of characters from the left to be evaluated.
/// </summary>
public int CharCount { get; }

#endregion

#region Equality and comparers

/// <summary>
/// Returns the hashcode for this <see cref="LeftQueryField"/>.
/// </summary>
/// <returns>The hashcode value.</returns>
public override int GetHashCode()
{
if (this.hashCode != null)
{
return this.hashCode.Value;
}

// Base
var hashCode = base.GetHashCode();

// CharCount
hashCode += CharCount.GetHashCode();

// Return
return (this.hashCode = hashCode).Value;
}

#endregion
}
}
49 changes: 49 additions & 0 deletions RepoDb.Core/RepoDb/Extensions/QueryFields/LeftTrimQueryField.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
using RepoDb.Enumerations;

namespace RepoDb.Extensions.QueryFields
{
/// <summary>
/// A functional-based <see cref="QueryField"/> object that is using the LTRIM function.
/// </summary>
public sealed class LeftTrimQueryField : FunctionalQueryField
{
#region Constructors

/// <summary>
/// Creates a new instance of <see cref="LeftTrimQueryField"/> object.
/// </summary>
/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftTrimQueryField(string fieldName,
string value)
: this(fieldName, Operation.Equal, value)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftTrimQueryField(Field field,
string value)
: this(field, Operation.Equal, value)
{ }

/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftTrimQueryField(string fieldName,
Operation operation,
string value)
: this(new Field(fieldName), operation, value)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LeftTrimQueryField(Field field,
Operation operation,
string value)
: base(field, operation, value, "LTRIM({0})")
{ }

#endregion
}
}
50 changes: 50 additions & 0 deletions RepoDb.Core/RepoDb/Extensions/QueryFields/LenQueryField.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
using RepoDb.Enumerations;

namespace RepoDb.Extensions.QueryFields
{
/// <summary>
/// A functional-based <see cref="QueryField"/> object that is using the LEN function.
/// This only works on SQL Server database provider.
/// </summary>
public sealed class LenQueryField : FunctionalQueryField
{
#region Constructors

/// <summary>
/// Creates a new instance of <see cref="LenQueryField"/> object.
/// </summary>
/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LenQueryField(string fieldName,
int value)
: this(fieldName, Operation.Equal, value)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LenQueryField(Field field,
int value)
: this(field, Operation.Equal, value)
{ }

/// <param name="fieldName">The name of the field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LenQueryField(string fieldName,
Operation operation,
int value)
: this(new Field(fieldName), operation, value)
{ }

/// <param name="field">The actual field for the query expression.</param>
/// <param name="operation">The operation to be used for the query expression.</param>
/// <param name="value">The value to be used for the query expression.</param>
public LenQueryField(Field field,
Operation operation,
int value)
: base(field, operation, value, "LEN({0})")
{ }

#endregion
}
}
Loading

0 comments on commit 095d02c

Please sign in to comment.