/// <summary> /// Queries CosmosDB for each of the token types /// sorts results based on location (if provided) and date /// </summary> public static IEnumerable <NoteModel> QueryNotes(string userId, string queryContents, string city, Point userLocation = null) { List <string> uniqueTokens = IndexerBase.GetDistinctTokens(queryContents).ToList(); if (uniqueTokens.Count == 0) { return(new List <NoteModel>()); } IQueryable <NoteModel> notes = CosmosDBClient.Query <NoteModel>().Where(n => n.UserId == userId); foreach (string token in uniqueTokens) { if (string.IsNullOrWhiteSpace(token)) { continue; } // Check each Indexer for membership if (new HashTagIndexer().IsMember(token)) { new HashTagIndexer().FilterNoteKeys(ref notes, token); TransactionModel.AddTransaction(userId, TransactionModel.TransactionType.Search, token, city, userLocation); continue; // index membership is disjoint } // Check each Indexer for membership if (new LocationIndexer().IsMember(token)) { new LocationIndexer().FilterNoteKeys(ref notes, token); continue; // index membership is disjoint } else if (new DateIndexer().IsMember(token)) { new DateIndexer().FilterNoteKeys(ref notes, token); continue; // index membership is disjoint } else if (new DateRangeIndexer().IsMember(token)) { // Date range is an exception where it's not stored as an actual index // but instead a range of indices new DateRangeIndexer().FilterNoteKeys(ref notes, token); continue; // index membership is disjoint } else { // Allow user to forget to add '#' when querying hashtags //new HashTagIndexer().FilterNoteKeys(ref notes, "#" + token); // Word is always the default token new WordIndexer().FilterNoteKeys(ref notes, token); } } return(notes); //// Build the query based on the tokens //if (userLocation != null) //{ // return notes.OrderByDescending(n => n.Location.Distance(userLocation)) // .ThenBy(n => n.LastUpdatedTime); //} //return notes.OrderByDescending(n => n.LastUpdatedTime); }
/// <summary> /// Updates the note and cleans up removed tags /// </summary> public static NoteModel UpdateNote(string userId, string noteId, string noteContents, string city, float latitude, float longitude, bool completed) { NoteModel note = CosmosDBClient.Query <NoteModel>() .Where(n => n.UserId == userId).Where(n => n.Id == noteId).AsEnumerable().FirstOrDefault(); if (note == default(NoteModel)) { return(null); } IEnumerable <string> removedTags; IEnumerable <string> newTags; note.SetNoteContents(noteContents, out removedTags, out newTags); // cleanup any removed tags (vast majority of the time user will not remove tags) foreach (string tag in removedTags) { TransactionModel.RemoveTransaction(userId, noteId, tag); } foreach (string tag in newTags) { TransactionModel.AddTransaction(userId, TransactionModel.TransactionType.Add, tag, city, latitude, longitude, noteId); } note.LastUpdatedTime = DateTime.UtcNow; if (note.City == null) { note.City = new HashSet <string>(); } if (!string.IsNullOrEmpty(city)) { note.City.Add(city); } note.Completed = completed; if (!CosmosDBClient.Update(note)) { return(null); } return(note); }
public NoteModel(string content, string city, float latitude, float longitude, string email, string userId) { Id = string.Concat("note_", DateTime.UtcNow.Ticks.ToString()); UserId = userId; IEnumerable <string> removedTags; IEnumerable <string> newTags; SetNoteContents(content, out removedTags, out newTags); foreach (string tag in newTags) { TransactionModel.AddTransaction(userId, TransactionModel.TransactionType.Add, tag, city, latitude, longitude, Id); } CreatedTime = DateTime.UtcNow; LastUpdatedTime = CreatedTime; City = new HashSet <string>(); if (!string.IsNullOrEmpty(city)) { City.Add(city.ToLowerInvariant()); } Completed = false; Location = new Point(longitude, latitude); // Performs special actions on note if applicable new ActionRunner().RunActions(email, DateTime.UtcNow, content, city); }