/// <summary> /// Overwrites a record. Used to update records. (or set the removed flag) /// </summary> /// <param name="mainFile">File stream of the dbset.</param> /// <param name="customInfos">To compare.</param> /// <param name="primitiveInfos">To compare.</param> /// <param name="orderedInfos">The infos in the order of being written to the file.</param> /// <param name="record">Record to be overwritten.</param> public static void Overwrite(Stream mainFile, BaseClass record) { int indexToBeInserted = record.id; mainFile.Position = record.RowSize() * (indexToBeInserted - 1); //gerekirse düzelt BinaryWriter bw = new BinaryWriter(mainFile); foreach (PropertyInfo info in record.OrderedInfos()) { if (record.PrimitiveInfos().Contains(info)) { WriteSingleProperty(bw, info, info.GetValue(record)); } else if (info.PropertyType.IsGenericType) { continue; } else { BaseClass child = (BaseClass)info.GetValue(record); if (child == null) { bw.Write(-1); } else { bw.Write(child.id); } } } }
/// <summary> /// Reads a single record from the file. Uses ReadSingleProperty method. /// </summary> /// <param name="mainFile">File stream of the dbset of the record</param> /// <param name="id">Id of the record to be read</param> /// <param name="t">Type of the record</param> /// <param name="primitiveInfos"></param> /// <param name="customInfos"></param> /// <param name="infos">Ordered info list to be read from the file.</param> /// <returns>Returns the record, and list of the childs to be read if exists.</returns> public static Tuple <BaseClass, Dictionary <PropertyInfo, int> > ReadSingleRecord(Stream mainFile, int id, Type t) { BaseClass trash = (BaseClass)Activator.CreateInstance(t); Dictionary <PropertyInfo, int> childObjects = new Dictionary <PropertyInfo, int>(); BaseClass record = (BaseClass)Activator.CreateInstance(t); BinaryReader br = new BinaryReader(mainFile); br.BaseStream.Position = trash.RowSize() * (id - 1); foreach (PropertyInfo info in trash.OrderedInfos()) { if (trash.OTORelInfos().Contains(info)) { childObjects.Add(info, (int)ReadSingleProperty(br, t, info)); } else { info.SetValue(record, ReadSingleProperty(br, t, info)); } } Tuple <BaseClass, Dictionary <PropertyInfo, int> > fillingLog = new Tuple <BaseClass, Dictionary <PropertyInfo, int> >(record, childObjects); //^object=record, Dictionary=property,fkid return(fillingLog); }
/// <summary> /// Inserts a record for the first time. Returns the id of last inserted record /// </summary> /// <param name="mainFile">Stream of the file, that holds the data for the DbSet of the record</param> /// <param name="removedIndexes">Empty index numbers in the file, can be filled with new records</param> /// <param name="infos">Properties that will be stored in database. (To exclude notmapped properties)</param> /// <param name="record">Record to be inserted</param> /// <returns>Returns the id of last inserted record</returns> public static int Add(Stream mainFile, List <int> removedIndexes, BaseClass record) { int indexToBeInserted = -1; if (removedIndexes.Count() > 0) { indexToBeInserted = removedIndexes[0]; Overwrite(mainFile, record); return(indexToBeInserted); } mainFile.Position = (mainFile.Length / record.RowSize()) * ((indexToBeInserted == -1) ? record.RowSize() : indexToBeInserted); // indexToBeInserted = Convert.ToInt32(mainFile.Position / record.RowSize()) + 1; //idler 1den başlasın BinaryWriter bw = new BinaryWriter(mainFile); foreach (PropertyInfo info in record.OrderedInfos()) { if (record.PrimitiveInfos().Contains(info)) { if (info.Name == "id") { WriteSingleProperty(bw, info, indexToBeInserted); } else { WriteSingleProperty(bw, info, info.GetValue(record)); } } else if (record.OTORelInfos().Contains(info)) { BaseClass child = (BaseClass)info.GetValue(record); if (child == null) { bw.Write(-1); } else { bw.Write(child.id); } } //one to many ise burada iş yok, dbset'te request yapılacak. } return(indexToBeInserted);//id dönecek }
public static void MakeReferenceNull(Stream mainFile, PropertyInfo info, Type T, Dictionary <int, List <int> > toChange) { //ToChange: //key = silinecek id //list int = key'e eskiden referans eden kayıtlar BaseClass trash = (BaseClass)Activator.CreateInstance(T); int total = 0; foreach (PropertyInfo orderedInfo in trash.OrderedInfos()) //sütun kaçıncı pozisyonda bul { if (orderedInfo.Name.Equals(info.Name)) //yazacağımız sütunu bulduk. { break; } else { if (trash.OTORelInfos().Contains(orderedInfo)) { total += sizeof(int); //foreign key } else if (orderedInfo.PropertyType == typeof(Boolean)) { total += 1; //marshal 4 döndürüyor, yanlışsın marshal. //dosyaya yazarken booleanlar 1 yer kaplıyor. } else if (orderedInfo.PropertyType == typeof(String)) { total += CustomAttr.GetLength(orderedInfo) + delimiter.Length; } else { total += System.Runtime.InteropServices.Marshal.SizeOf(orderedInfo.PropertyType); } } } BinaryWriter bw = new BinaryWriter(mainFile); foreach (KeyValuePair <int, List <int> > kp in toChange) { foreach (int id in kp.Value) { bw.BaseStream.Position = (id - 1) * trash.RowSize() + total; bw.Write(-1); } } }
public void ReadAll(bool ReadRemoved = false) { allRecords = new List <T>(); OpenMainRead(); BaseClass trash = (BaseClass)Activator.CreateInstance(typeof(T)); int line = Convert.ToInt32(mainFile.Length) / trash.RowSize(); for (int id = 0; id < line; id++) { Tuple <BaseClass, Dictionary <PropertyInfo, int> > fillingLog; fillingLog = FileOps.ReadSingleRecord(mainFile, id + 1, typeof(T)); BaseClass rec = fillingLog.Item1; if (ReadRemoved || !rec.removed) { allRecords.Add((T)rec); foreach (KeyValuePair <PropertyInfo, int> kp in fillingLog.Item2) //OTOReq'ler { object dbset = ctx.GetDBSetByType(kp.Key.PropertyType); if (kp.Value == -1) //null, okumaya çalışma! { continue; } Tuple <object, PropertyInfo, int> RecordToBeFilled = new Tuple <object, PropertyInfo, int>(fillingLog.Item1, kp.Key, kp.Value); object[] parameters = { new OTOReq(fillingLog.Item1, kp.Key, kp.Value) }; dbset.GetType().GetMethod("AddOTOReq").Invoke(dbset, parameters); } foreach (PropertyInfo OTM in trash.OTM_One()) { if (OTM.GetValue(fillingLog.Item1) == null) { OTM.SetValue(OTM.GetValue(fillingLog.Item1), Activator.CreateInstance(OTM.PropertyType)); } object dbset = ctx.GetDBSetByType(OTM.PropertyType.GetGenericArguments()[0]); object[] parameters = { new Tuple <object, PropertyInfo>(fillingLog.Item1, OTM) }; dbset.GetType().GetMethod("AddOTMReq").Invoke(dbset, parameters); } //MTM ReadMTM(fillingLog.Item1); } } mainFile.Close(); }