Example #1
0
        public TagModule(IMyDbContext context) : base("/tags")
        {
            this.RequiresAuthentication();

            Get["/", true] = async(_, token) => await context.Tags.ToListAsync(token).ConfigureAwait(false);

            Post["/"] = _ =>
            {
                var tag = this.BindAndValidate <Tag>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                context.Tags.Add(tag);
                context.SaveChanges();

                //return the object with the id after inserting
                return(tag);
            };

            Put["/"] = _ =>
            {
                var newTag = this.BindAndValidate <Tag>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                //make sure the tag we want to update exists
                var tag = context.Tags.FirstOrDefault(x => x.ID == newTag.ID);
                if (tag == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                //update values
                context.UpdateEntryValues(tag, newTag);

                context.SaveChanges();

                return(tag);
            };

            Delete["/{Id:int}"] = parameters =>
            {
                int id  = parameters.Id;
                var tag = context.Tags.FirstOrDefault(x => x.ID == id);

                if (tag == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                context.Tags.Remove(tag);
                context.SaveChanges();

                return(tag);
            };
        }
Example #2
0
        /// <summary>
        /// Updates a collection, adding/removing values. The entities in the collection are assumed to be attached/tracked.
        /// newValues need not already exist.
        /// Also updates the fields of each element.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="collection"></param>
        /// <param name="newValues"></param>
        /// <param name="context"></param>
        public static void UpdateCollectionAndElements <T>(this ICollection <T> collection, IEnumerable <T> newValues, IMyDbContext context) where T : class, IEntity
        {
            //remove those that need to be removed
            var toRemove = collection.Where(x => !newValues.Any(y => y.ID == x.ID)).ToList();

            foreach (T item in toRemove)
            {
                context.SetEntryState(item, EntityState.Deleted);
            }

            //find the ones that overlap and add or update them
            foreach (T item in newValues)
            {
                if (item.ID == 0) //this means it's newly added
                {
                    collection.Add(item);
                }
                else //this is an existing entity, update it
                {
                    var attached = collection.FirstOrDefault(x => x.ID == item.ID); //no need for Entry()/Attach() -  these are already in the ObjectStateManager
                    if (attached == null)
                    {
                        continue;                   //if the collection on the server has been changed and the client tries to update a deleted element, you can end up in this scenario...just skip it
                    }
                    context.UpdateEntryValues(attached, item);
                }
            }
        }
Example #3
0
        /// <summary>
        ///     Updates the instrument with new values.
        /// </summary>
        public async Task UpdateInstrument(Instrument attachedInstrument, Instrument newValues)
        {
            if (attachedInstrument == null)
            {
                throw new ArgumentNullException(nameof(attachedInstrument));
            }
            if (newValues == null)
            {
                throw new ArgumentNullException(nameof(newValues));
            }

            ValidateInstrument(newValues);

            Context.UpdateEntryValues(attachedInstrument, newValues);

            attachedInstrument.Tags.UpdateCollection(newValues.Tags, Context);

            if (newValues.SessionsSource == SessionsSource.Custom)
            {
                //todo
                //attachedInstrument.InstrumentInstrumentSessions.UpdateCollectionAndElements(newValues.Sessions, Context);
            }

            await Context.DbContext.SaveChangesAsync().ConfigureAwait(false);
        }
Example #4
0
        /// <summary>
        /// Updates the instrument with new values.
        /// </summary>
        public async Task UpdateInstrument(Instrument attachedInstrument, Instrument newValues)
        {
            if (attachedInstrument == null)
            {
                throw new ArgumentNullException(nameof(attachedInstrument));
            }
            if (newValues == null)
            {
                throw new ArgumentNullException(nameof(newValues));
            }

            ValidateInstrument(newValues);

            //update it
            Context.UpdateEntryValues(attachedInstrument, newValues);

            //Update tags
            attachedInstrument.Tags.UpdateCollection(newValues.Tags, Context);

            //Update sessions
            if (newValues.SessionsSource == SessionsSource.Custom)
            {
                attachedInstrument.Sessions.UpdateCollectionAndElements(newValues.Sessions, Context);
            }

            //Continuous future object
            if (attachedInstrument.IsContinuousFuture)
            {
                Context.UpdateEntryValues(attachedInstrument.ContinuousFuture, newValues.ContinuousFuture);
                var rootSymbol = Context.UnderlyingSymbols.Find(newValues.ContinuousFuture.UnderlyingSymbolID);
                attachedInstrument.ContinuousFuture.UnderlyingSymbol = rootSymbol;
            }

            //Exchange/PrimaryExchange/Datasource just works (because they work by the ID properties), we don't need to do any attaching

            //save it
            await Context.SaveChangesAsync().ConfigureAwait(false);
        }
Example #5
0
        public ExchangeModule(IMyDbContext context) : base("/exchanges")
        {
            this.RequiresAuthentication();

            var dbSet = context.Set <Exchange>();

            Get("/", async(_, token) => await dbSet.Include(x => x.Sessions).ToListAsync(token).ConfigureAwait(false));

            Get("/{Id:int}", parameters =>
            {
                var id       = (int)parameters.Id;
                var exchange = dbSet.Include(x => x.Sessions).FirstOrDefault(x => x.ID == id);

                if (exchange == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                return(exchange);
            });

            Post("/", _ =>
            {
                Exchange exchange = this.BindAndValidate <Exchange>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                dbSet.Add(exchange);
                context.SaveChanges();

                //return the object with the id after inserting
                return(exchange);
            });

            Put("/", _ =>
            {
                Exchange newValues = this.BindAndValidate <Exchange>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                //make sure the exchange we want to update exists
                var exchange = dbSet.Include(x => x.Sessions).FirstOrDefault(x => x.ID == newValues.ID);
                if (exchange == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                //update values on the exchange
                context.UpdateEntryValues(exchange, newValues);

                //add/remove/update the Sessions collection
                exchange.Sessions.UpdateCollectionAndElements(newValues.Sessions, context);

                //some instruments may have their sessions based on this exchange, we need to update them
                var instruments = context.Set <Instrument>()
                                  .Where(x => x.SessionsSource == SessionsSource.Exchange && x.ExchangeID == exchange.ID).ToList();

                foreach (Instrument i in instruments)
                {
                    context.Set <InstrumentSession>().RemoveRange(i.Sessions);
                    i.Sessions.Clear();

                    foreach (ExchangeSession s in exchange.Sessions)
                    {
                        i.Sessions.Add(s.ToInstrumentSession());
                    }
                }

                context.SaveChanges();

                return(exchange);
            });

            Delete("/{Id:int}", parameters =>
            {
                int id       = parameters.Id;
                var exchange = dbSet.FirstOrDefault(x => x.ID == id);

                if (exchange == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                var exchangeReferenced = context.Set <Instrument>().Any(x => x.ExchangeID == id || x.PrimaryExchangeID == id);
                if (exchangeReferenced)
                {
                    return(Negotiate
                           .WithModel(new ErrorResponse(
                                          HttpStatusCode.Conflict,
                                          "Can't delete this exchange because it has instruments assigned to it.", ""))
                           .WithStatusCode(HttpStatusCode.Conflict));
                }

                dbSet.Remove(exchange);
                context.SaveChanges();
                return(exchange);
            });
        }
Example #6
0
        public UnderlyingSymbolModule(IMyDbContext context) : base("/underlyingsymbols")
        {
            this.RequiresAuthentication();
            var dbSet = context.Set <UnderlyingSymbol>();

            Get("/", _ => dbSet.ToList());

            Get("/{Id:int}", parameters =>
            {
                var id       = (int)parameters.Id;
                var exchange = dbSet.FirstOrDefault(x => x.ID == id);

                if (exchange == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                return(exchange);
            });

            Put("/", _ =>
            {
                UnderlyingSymbol newValues = this.BindAndValidate <UnderlyingSymbol>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                //make sure the exchange we want to update exists
                var symbol = dbSet.FirstOrDefault(x => x.ID == newValues.ID);
                if (symbol == null)
                {
                    return(HttpStatusCode.NotFound);
                }


                //update values on the exchange
                context.UpdateEntryValues(symbol, newValues);

                context.SaveChanges();

                return(symbol);
            });

            Post("/", _ =>
            {
                UnderlyingSymbol symbol = this.BindAndValidate <UnderlyingSymbol>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                dbSet.Add(symbol);
                context.SaveChanges();

                //return the object with the id after inserting
                return(symbol);
            });

            Delete("/{Id:int}", parameters =>
            {
                int id     = parameters.Id;
                var symbol = dbSet.FirstOrDefault(x => x.ID == id);

                if (symbol == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                var symbolReferenced = context.Set <ContinuousFuture>().Any(x => x.UnderlyingSymbolID == id);
                if (symbolReferenced)
                {
                    return(Negotiate
                           .WithModel(new ErrorResponse(
                                          HttpStatusCode.Conflict,
                                          "Can't delete this underlying symbol because it has continuous futures assigned to it.", ""))
                           .WithStatusCode(HttpStatusCode.Conflict));
                }

                dbSet.Remove(symbol);
                context.SaveChanges();
                return(symbol);
            });
        }
Example #7
0
        public SessionTemplateModule(IMyDbContext context) : base("/sessiontemplates")
        {
            this.RequiresAuthentication();

            var dbSet = context.Set <SessionTemplate>();

            Get["/", runAsync : true] = async(_, token) => await dbSet.Include(x => x.Sessions).ToListAsync(token).ConfigureAwait(false);

            Post["/"] = _ =>
            {
                SessionTemplate template = this.BindAndValidate <SessionTemplate>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                dbSet.Add(template);
                context.SaveChanges();

                //return the object with the id after inserting
                return(template);
            };

            Put["/"] = _ =>
            {
                SessionTemplate newValues = this.BindAndValidate <SessionTemplate>();
                if (ModelValidationResult.IsValid == false)
                {
                    return(this.ValidationFailure());
                }

                //make sure the template we want to update exists
                var template = dbSet.Include(x => x.Sessions).FirstOrDefault(x => x.ID == newValues.ID);
                if (template == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                //update values on the template
                context.UpdateEntryValues(template, newValues);

                //add/remove/update the Sessions collection
                template.Sessions.UpdateCollectionAndElements(newValues.Sessions, context);

                //some instruments may have their sessions based on this template, we need to update them
                var instruments = context.Set <Instrument>()
                                  .Where(x => x.SessionsSource == SessionsSource.Template && x.SessionTemplateID == template.ID).ToList();
                foreach (Instrument i in instruments)
                {
                    context.Set <InstrumentSession>().RemoveRange(i.Sessions);
                    i.Sessions.Clear();

                    foreach (TemplateSession s in template.Sessions)
                    {
                        i.Sessions.Add(s.ToInstrumentSession());
                    }
                }

                context.SaveChanges();

                return(template);
            };

            Delete["/{Id:int}"] = parameters =>
            {
                //It's possible to delete
                int id       = parameters.Id;
                var template = dbSet.FirstOrDefault(x => x.ID == id);

                if (template == null)
                {
                    return(HttpStatusCode.NotFound);
                }

                //make sure there are no references to it
                var templateReferenced = context.Set <Instrument>().Any(x => x.SessionTemplateID == id && x.SessionsSource == SessionsSource.Template);
                if (templateReferenced)
                {
                    return(Negotiate
                           .WithModel(new ErrorResponse(
                                          HttpStatusCode.Conflict,
                                          "Can't delete this template because it has instruments assigned to it.", ""))
                           .WithStatusCode(HttpStatusCode.Conflict));
                }

                dbSet.Remove(template);
                context.SaveChanges();
                return(template);
            };
        }