You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
206 lines
5.7 KiB
206 lines
5.7 KiB
// Copyright (c) 2004-2008 MySQL AB, 2008-2009 Sun Microsystems, Inc.
|
|
//
|
|
// This program is free software; you can redistribute it and/or modify
|
|
// it under the terms of the GNU General Public License version 2 as published by
|
|
// the Free Software Foundation
|
|
//
|
|
// There are special exceptions to the terms and conditions of the GPL
|
|
// as it is applied to this software. View the full text of the
|
|
// exception in file EXCEPTIONS in the directory of this software
|
|
// distribution.
|
|
//
|
|
// This program is distributed in the hope that it will be useful,
|
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
// GNU General Public License for more details.
|
|
//
|
|
// You should have received a copy of the GNU General Public License
|
|
// along with this program; if not, write to the Free Software
|
|
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
|
|
using System;
|
|
using System.Data;
|
|
using MySql.Data.MySqlClient;
|
|
|
|
namespace MySql.Data.Types
|
|
{
|
|
internal struct MySqlTimeSpan : IMySqlValue
|
|
{
|
|
private TimeSpan mValue;
|
|
private bool isNull;
|
|
|
|
public MySqlTimeSpan(bool isNull)
|
|
{
|
|
this.isNull = isNull;
|
|
mValue = TimeSpan.MinValue;
|
|
}
|
|
|
|
public MySqlTimeSpan(TimeSpan val)
|
|
{
|
|
this.isNull = false;
|
|
mValue = val;
|
|
}
|
|
|
|
#region IMySqlValue Members
|
|
|
|
public bool IsNull
|
|
{
|
|
get { return isNull; }
|
|
}
|
|
|
|
MySqlDbType IMySqlValue.MySqlDbType
|
|
{
|
|
get { return MySqlDbType.Time; }
|
|
}
|
|
|
|
DbType IMySqlValue.DbType
|
|
{
|
|
get { return DbType.Time; }
|
|
}
|
|
|
|
object IMySqlValue.Value
|
|
{
|
|
get { return mValue; }
|
|
}
|
|
|
|
public TimeSpan Value
|
|
{
|
|
get { return mValue; }
|
|
}
|
|
|
|
Type IMySqlValue.SystemType
|
|
{
|
|
get { return typeof(TimeSpan); }
|
|
}
|
|
|
|
string IMySqlValue.MySqlTypeName
|
|
{
|
|
get { return "TIME"; }
|
|
}
|
|
|
|
void IMySqlValue.WriteValue(MySqlPacket packet, bool binary, object val, int length)
|
|
{
|
|
if (!(val is TimeSpan))
|
|
throw new MySqlException("Only TimeSpan objects can be serialized by MySqlTimeSpan");
|
|
|
|
TimeSpan ts = (TimeSpan)val;
|
|
bool negative = ts.TotalMilliseconds < 0;
|
|
ts = ts.Duration();
|
|
|
|
if (binary)
|
|
{
|
|
packet.WriteByte(8);
|
|
packet.WriteByte((byte)(negative ? 1 : 0));
|
|
packet.WriteInteger(ts.Days, 4);
|
|
packet.WriteByte((byte)ts.Hours);
|
|
packet.WriteByte((byte)ts.Minutes);
|
|
packet.WriteByte((byte)ts.Seconds);
|
|
}
|
|
else
|
|
{
|
|
String s = String.Format("'{0}{1} {2:00}:{3:00}:{4:00}.{5}'",
|
|
negative ? "-" : "", ts.Days, ts.Hours, ts.Minutes, ts.Seconds, ts.Milliseconds);
|
|
|
|
packet.WriteStringNoNull(s);
|
|
}
|
|
}
|
|
|
|
|
|
IMySqlValue IMySqlValue.ReadValue(MySqlPacket packet, long length, bool nullVal)
|
|
{
|
|
if (nullVal) return new MySqlTimeSpan(true);
|
|
|
|
if (length >= 0)
|
|
{
|
|
string value = packet.ReadString(length);
|
|
ParseMySql(value, packet.Version.isAtLeast(4, 1, 0));
|
|
return this;
|
|
}
|
|
|
|
long bufLength = packet.ReadByte();
|
|
int negate = 0;
|
|
if (bufLength > 0)
|
|
negate = packet.ReadByte();
|
|
|
|
isNull = false;
|
|
if (bufLength == 0)
|
|
isNull = true;
|
|
else if (bufLength == 5)
|
|
mValue = new TimeSpan(packet.ReadInteger(4), 0, 0, 0);
|
|
else if (bufLength == 8)
|
|
mValue = new TimeSpan(packet.ReadInteger(4),
|
|
packet.ReadByte(), packet.ReadByte(), packet.ReadByte());
|
|
else
|
|
mValue = new TimeSpan(packet.ReadInteger(4),
|
|
packet.ReadByte(), packet.ReadByte(), packet.ReadByte(),
|
|
packet.ReadInteger(4) / 1000000);
|
|
|
|
if (negate == 1)
|
|
mValue = mValue.Negate();
|
|
return this;
|
|
}
|
|
|
|
void IMySqlValue.SkipValue(MySqlPacket packet)
|
|
{
|
|
int len = packet.ReadByte();
|
|
packet.Position += len;
|
|
}
|
|
|
|
#endregion
|
|
|
|
internal static void SetDSInfo(DataTable dsTable)
|
|
{
|
|
// we use name indexing because this method will only be called
|
|
// when GetSchema is called for the DataSourceInformation
|
|
// collection and then it wil be cached.
|
|
DataRow row = dsTable.NewRow();
|
|
row["TypeName"] = "TIME";
|
|
row["ProviderDbType"] = MySqlDbType.Time;
|
|
row["ColumnSize"] = 0;
|
|
row["CreateFormat"] = "TIME";
|
|
row["CreateParameters"] = null;
|
|
row["DataType"] = "System.TimeSpan";
|
|
row["IsAutoincrementable"] = false;
|
|
row["IsBestMatch"] = true;
|
|
row["IsCaseSensitive"] = false;
|
|
row["IsFixedLength"] = true;
|
|
row["IsFixedPrecisionScale"] = true;
|
|
row["IsLong"] = false;
|
|
row["IsNullable"] = true;
|
|
row["IsSearchable"] = true;
|
|
row["IsSearchableWithLike"] = false;
|
|
row["IsUnsigned"] = false;
|
|
row["MaximumScale"] = 0;
|
|
row["MinimumScale"] = 0;
|
|
row["IsConcurrencyType"] = DBNull.Value;
|
|
row["IsLiteralSupported"] = false;
|
|
row["LiteralPrefix"] = null;
|
|
row["LiteralSuffix"] = null;
|
|
row["NativeDataType"] = null;
|
|
dsTable.Rows.Add(row);
|
|
}
|
|
|
|
public override string ToString()
|
|
{
|
|
return String.Format("{0} {1:00}:{2:00}:{3:00}.{4}",
|
|
mValue.Days, mValue.Hours, mValue.Minutes, mValue.Seconds, mValue.Milliseconds);
|
|
}
|
|
|
|
private void ParseMySql(string s, bool is41)
|
|
{
|
|
string[] parts = s.Split(':');
|
|
int hours = Int32.Parse(parts[0]);
|
|
int mins = Int32.Parse(parts[1]);
|
|
int secs = Int32.Parse(parts[2]);
|
|
if (hours < 0 || parts[0].StartsWith("-"))
|
|
{
|
|
mins *= -1;
|
|
secs *= -1;
|
|
}
|
|
int days = hours / 24;
|
|
hours = hours - (days * 24);
|
|
mValue = new TimeSpan(days, hours, mins, secs, 0);
|
|
isNull = false;
|
|
}
|
|
}
|
|
}
|
|
|