opensim-development – Blame information for rev 1

Subversion Repositories:
Rev:
Rev Author Line No. Line
1 eva 1 /*
2 * Copyright (c) Contributors, http://opensimulator.org/
3 * See CONTRIBUTORS.TXT for a full list of copyright holders.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * * Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * * Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * * Neither the name of the OpenSimulator Project nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY
17 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY
20 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
23 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 */
27  
28 using System;
29 using System.Data;
30 using System.Data.SqlClient;
31 using System.Reflection;
32 using System.Collections.Generic;
33 using OpenMetaverse;
34 using log4net;
35 using OpenSim.Framework;
36  
37 namespace OpenSim.Data.MSSQL
38 {
39 /// <summary>
40 /// A MSSQL Interface for the Asset server
41 /// </summary>
42 public class MSSQLAssetData : AssetDataBase
43 {
44 private const string _migrationStore = "AssetStore";
45  
46 private static readonly ILog m_log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
47 private long m_ticksToEpoch;
48 /// <summary>
49 /// Database manager
50 /// </summary>
51 private MSSQLManager m_database;
52 private string m_connectionString;
53  
54 #region IPlugin Members
55  
56 override public void Dispose() { }
57  
58 /// <summary>
59 /// <para>Initialises asset interface</para>
60 /// </summary>
61 // [Obsolete("Cannot be default-initialized!")]
62 override public void Initialise()
63 {
64 m_log.Info("[MSSQLAssetData]: " + Name + " cannot be default-initialized!");
65 throw new PluginNotInitialisedException(Name);
66 }
67  
68 /// <summary>
69 /// Initialises asset interface
70 /// </summary>
71 /// <para>
72 /// a string instead of file, if someone writes the support
73 /// </para>
74 /// <param name="connectionString">connect string</param>
75 override public void Initialise(string connectionString)
76 {
77 m_ticksToEpoch = new System.DateTime(1970, 1, 1).Ticks;
78  
79 m_database = new MSSQLManager(connectionString);
80 m_connectionString = connectionString;
81  
82 //New migration to check for DB changes
83 m_database.CheckMigration(_migrationStore);
84 }
85  
86 /// <summary>
87 /// Database provider version.
88 /// </summary>
89 override public string Version
90 {
91 get { return m_database.getVersion(); }
92 }
93  
94 /// <summary>
95 /// The name of this DB provider.
96 /// </summary>
97 override public string Name
98 {
99 get { return "MSSQL Asset storage engine"; }
100 }
101  
102 #endregion
103  
104 #region IAssetDataPlugin Members
105  
106 /// <summary>
107 /// Fetch Asset from m_database
108 /// </summary>
109 /// <param name="assetID">the asset UUID</param>
110 /// <returns></returns>
111 override public AssetBase GetAsset(UUID assetID)
112 {
113 string sql = "SELECT * FROM assets WHERE id = @id";
114 using (SqlConnection conn = new SqlConnection(m_connectionString))
115 using (SqlCommand cmd = new SqlCommand(sql, conn))
116 {
117 cmd.Parameters.Add(m_database.CreateParameter("id", assetID));
118 conn.Open();
119 using (SqlDataReader reader = cmd.ExecuteReader())
120 {
121 if (reader.Read())
122 {
123 AssetBase asset = new AssetBase(
124 DBGuid.FromDB(reader["id"]),
125 (string)reader["name"],
126 Convert.ToSByte(reader["assetType"]),
127 reader["creatorid"].ToString()
128 );
129 // Region Main
130 asset.Description = (string)reader["description"];
131 asset.Local = Convert.ToBoolean(reader["local"]);
132 asset.Temporary = Convert.ToBoolean(reader["temporary"]);
133 asset.Flags = (AssetFlags)(Convert.ToInt32(reader["asset_flags"]));
134 asset.Data = (byte[])reader["data"];
135 return asset;
136 }
137 return null; // throw new Exception("No rows to return");
138 }
139 }
140 }
141  
142 /// <summary>
143 /// Create asset in m_database
144 /// </summary>
145 /// <param name="asset">the asset</param>
146 override public void StoreAsset(AssetBase asset)
147 {
148  
149 string sql =
150 @"IF EXISTS(SELECT * FROM assets WHERE id=@id)
151 UPDATE assets set name = @name, description = @description, assetType = @assetType,
152 local = @local, temporary = @temporary, creatorid = @creatorid, data = @data
153 WHERE id=@id
154 ELSE
155 INSERT INTO assets
156 ([id], [name], [description], [assetType], [local],
157 [temporary], [create_time], [access_time], [creatorid], [asset_flags], [data])
158 VALUES
159 (@id, @name, @description, @assetType, @local,
160 @temporary, @create_time, @access_time, @creatorid, @asset_flags, @data)";
161  
162 string assetName = asset.Name;
163 if (asset.Name.Length > 64)
164 {
165 assetName = asset.Name.Substring(0, 64);
166 m_log.WarnFormat(
167 "[ASSET DB]: Name '{0}' for asset {1} truncated from {2} to {3} characters on add",
168 asset.Name, asset.ID, asset.Name.Length, assetName.Length);
169 }
170  
171 string assetDescription = asset.Description;
172 if (asset.Description.Length > 64)
173 {
174 assetDescription = asset.Description.Substring(0, 64);
175 m_log.WarnFormat(
176 "[ASSET DB]: Description '{0}' for asset {1} truncated from {2} to {3} characters on add",
177 asset.Description, asset.ID, asset.Description.Length, assetDescription.Length);
178 }
179  
180 using (SqlConnection conn = new SqlConnection(m_connectionString))
181 using (SqlCommand command = new SqlCommand(sql, conn))
182 {
183 int now = (int)((System.DateTime.Now.Ticks - m_ticksToEpoch) / 10000000);
184 command.Parameters.Add(m_database.CreateParameter("id", asset.FullID));
185 command.Parameters.Add(m_database.CreateParameter("name", assetName));
186 command.Parameters.Add(m_database.CreateParameter("description", assetDescription));
187 command.Parameters.Add(m_database.CreateParameter("assetType", asset.Type));
188 command.Parameters.Add(m_database.CreateParameter("local", asset.Local));
189 command.Parameters.Add(m_database.CreateParameter("temporary", asset.Temporary));
190 command.Parameters.Add(m_database.CreateParameter("access_time", now));
191 command.Parameters.Add(m_database.CreateParameter("create_time", now));
192 command.Parameters.Add(m_database.CreateParameter("asset_flags", (int)asset.Flags));
193 command.Parameters.Add(m_database.CreateParameter("creatorid", asset.Metadata.CreatorID));
194 command.Parameters.Add(m_database.CreateParameter("data", asset.Data));
195 conn.Open();
196 try
197 {
198 command.ExecuteNonQuery();
199 }
200 catch(Exception e)
201 {
202 m_log.Error("[ASSET DB]: Error storing item :" + e.Message);
203 }
204 }
205 }
206  
207  
208 // Commented out since currently unused - this probably should be called in GetAsset()
209 // private void UpdateAccessTime(AssetBase asset)
210 // {
211 // using (AutoClosingSqlCommand cmd = m_database.Query("UPDATE assets SET access_time = @access_time WHERE id=@id"))
212 // {
213 // int now = (int)((System.DateTime.Now.Ticks - m_ticksToEpoch) / 10000000);
214 // cmd.Parameters.AddWithValue("@id", asset.FullID.ToString());
215 // cmd.Parameters.AddWithValue("@access_time", now);
216 // try
217 // {
218 // cmd.ExecuteNonQuery();
219 // }
220 // catch (Exception e)
221 // {
222 // m_log.Error(e.ToString());
223 // }
224 // }
225 // }
226  
227 /// <summary>
228 /// Check if asset exist in m_database
229 /// </summary>
230 /// <param name="uuid"></param>
231 /// <returns>true if exist.</returns>
232 override public bool ExistsAsset(UUID uuid)
233 {
234 if (GetAsset(uuid) != null)
235 {
236 return true;
237 }
238 return false;
239 }
240  
241 /// <summary>
242 /// Returns a list of AssetMetadata objects. The list is a subset of
243 /// the entire data set offset by <paramref name="start" /> containing
244 /// <paramref name="count" /> elements.
245 /// </summary>
246 /// <param name="start">The number of results to discard from the total data set.</param>
247 /// <param name="count">The number of rows the returned list should contain.</param>
248 /// <returns>A list of AssetMetadata objects.</returns>
249 public override List<AssetMetadata> FetchAssetMetadataSet(int start, int count)
250 {
251 List<AssetMetadata> retList = new List<AssetMetadata>(count);
252 string sql = @"WITH OrderedAssets AS
253 (
254 SELECT id, name, description, assetType, temporary, creatorid,
255 RowNumber = ROW_NUMBER() OVER (ORDER BY id)
256 FROM assets
257 )
258 SELECT *
259 FROM OrderedAssets
260 WHERE RowNumber BETWEEN @start AND @stop;";
261  
262 using (SqlConnection conn = new SqlConnection(m_connectionString))
263 using (SqlCommand cmd = new SqlCommand(sql, conn))
264 {
265 cmd.Parameters.Add(m_database.CreateParameter("start", start));
266 cmd.Parameters.Add(m_database.CreateParameter("stop", start + count - 1));
267 conn.Open();
268 using (SqlDataReader reader = cmd.ExecuteReader())
269 {
270 while (reader.Read())
271 {
272 AssetMetadata metadata = new AssetMetadata();
273 metadata.FullID = DBGuid.FromDB(reader["id"]);
274 metadata.Name = (string)reader["name"];
275 metadata.Description = (string)reader["description"];
276 metadata.Type = Convert.ToSByte(reader["assetType"]);
277 metadata.Temporary = Convert.ToBoolean(reader["temporary"]);
278 metadata.CreatorID = (string)reader["creatorid"];
279 retList.Add(metadata);
280 }
281 }
282 }
283  
284 return retList;
285 }
286  
287 public override bool Delete(string id)
288 {
289 return false;
290 }
291 #endregion
292 }
293 }