I am trying to write a method which would return all the Book documents from the MongoDB to my mvc application. First, I connect to database, retrieve collection and convert that collection into Json file. Next I create a list which has couple fields specified (name, author, etc.) using serializer i try to deserialize it into list and using a for loop return the list of books. Sadly I get error in the return line (convertion error). Any suggests are welcomed!
public List<Book> getAllBooks()
{
var mongoClient = new MongoClient("mongodb://localhost");
var database = mongoClient.GetDatabase("SearchForKnowledge");
var coll = database.GetCollection<BsonDocument>("Book");
coll.ToJson();
List<Book> collection = new List<Book>();
JavaScriptSerializer js = new JavaScriptSerializer();
collection = (List<Book>)Newtonsoft.Json.JsonConvert.DeserializeObject(coll.ToString());
for (int i = 0; i < collection.Count(); i++)
{
return collection[i];
}
}
well, you should try simpler way:
// add this using first
using MongoDB.Driver.Linq;
var coll = database.GetCollection<Book>("Book").AsQueryable<Book>();
And than you can do anything, e.g:
var someBooks = coll.Where(b => b.Year == 2014).Skip(0).Take(10).ToArray();
PS: You need to check out this tutorial: https://mongodb-documentation.readthedocs.org/en/latest/ecosystem/tutorial/use-linq-queries-with-csharp-driver.html
Related
I'm getting the mentioned error when trying to DeserializeObject() into a list of strings.
ResultSet is fine and making a string as:
string sRetVal_Json = new JavaScriptSerializer().Serialize(ResultSet);
also works fine.
The resultant string, e.g., is:
sRetVal_Json = "[{\"CUSTNUM\":\"8690\"}]"
Here is a code snip:
var ResultSet = (from cms in MASadminE.MOM_CMS
where cms.ORDER == sOrdNum
select new
{
cms.CUSTNUM
});
List<string> list = new List<string>();
string sRetVal_Json = new JavaScriptSerializer().Serialize(ResultSet);
if (sRetVal_Json != "[]") // got > 0 records
{
list = JsonConvert.DeserializeObject<List<string>>(sRetVal_Json);
}
You're trying to deserialize a serialized list of anonymously-typed objects to a list of strings. The parser chokes when it hits the colon after the first property name. I don't think there's a way to use NewtonSoft to deserialize to a list of an anonymous type. You can deserialize to a Dictionary<string, string>, though:
Dictionary<string, string>> dict = JsonConvert.DeserializeObject<Dictionary<string, string>>>(sRetVal_Json);
It doesn't make sense to serialize and then deserialize to get your list of strings. You still have the same problem and you're just doing unecessary processing.
Change your projection to just select the value if that is all you want. Then ToList() it if there are any items in the sequence:
var ResultSet = (from cms in MASadminE.MOM_CMS
where cms.ORDER == sOrdNum
select cms.CUSTNUM);
if(ResultSet.Any())
{
List<string> custnums = ResultSet.ToList();
}
The issue is that the ResultSet here is actually the "dynamic" type because you created an anonymous class when you did
select new
{
cms.CUSTNUM
}
Thus there are 2 ways to do this. Either change your select to select back cms.CUSTNUM directly to get a list of strings (but JSON won't have CUSTNUM as a property) or you create a class that will support you here.
1.
var ResultSet = (from cms in MASadminE.MOM_CMS
where cms.ORDER == sOrdNum
select cms.CUSTNUM).ToList();
(Then you can use List< string > here)
2.
public class MyData
{
public string CUSTNUM { get; set; }
}
var ResultSet = (from cms in MASadminE.MOM_CMS
where cms.ORDER == sOrdNum
select new MyData
{
CUSTNUM = cms.CUSTNUM
});
List<MyData> list = new List<MyData>();
string sRetVal_Json = new JavaScriptSerializer().Serialize(ResultSet);
if (sRetVal_Json != "[]") // got > 0 records
{
list = JsonConvert.DeserializeObject<List<MyData>>(sRetVal_Json);
}
I have documents:
{"handler":"north"}
{"handler":"south"}
{"handler":"west"}
{"handler":"east"}
I want to find a matching handler from a given string input, e.g. "westtown" and expects the handler will be "west".
Please help, my code below does not work.
String inputstring = "westtown";
IMongoCollection<BsonDocument> collection = null;
List<BsonDocument> pages = null;
try
{
collection = db.GetCollection<BsonDocument>("handlers");
pages = await collection.Find(x => (inputstring.StartsWith(x["handler"].AsString))).ToListAsync<BsonDocument>();
}
...
I use classless scheme, so I use BsonDocument on the dynamic.
AFAIK, In MongoDB you can find it with $where operator like this:
{ $where: "'westtown'.startsWith(this.handler)" }
So, I think in c# you can do it with something like this:
var filter =
new BsonDocument(
new Dictionary<string, BsonValue>
{
{
"$where",
new BsonString("'westtown'.startsWith(this.handler)")
}
});
var result = col.Find(filter).ToList();
I try to get all data from collection into MongoDB server using C# driver.
The idea is connect to the server and get all collection than insert into list of class.
List<WatchTblCls> wts;
List<UserCls> users;
List<SymboleCls> syms;
public WatchTbl()
{
InitializeComponent();
wts = new List<WatchTblCls>();
users = new List<UserCls>();
syms = new List<SymboleCls>();
}
public async void getAllData()
{
client = new MongoClient("mongodb://servername:27017");
database = client.GetDatabase("WatchTblDB");
collectionWatchtbl = database.GetCollection<WatchTbl>("Watchtbl");
collectionUser = database.GetCollection<UserCls>("Users");
collectionSymbole = database.GetCollection<SymboleCls>("Users");
var filter = new BsonDocument();
using (var cursor = await collectionWatchtbl.FindAsync(filter))
{
while (await cursor.MoveNextAsync())
{
var batch = cursor.Current;
foreach (var document in batch)
{
wts.Add(new WatchTblCls(document["_id"], document["userId"], document["wid"], document["name"], document["Symboles"]));
}
}
}
}
I get this error under
wts.Add(new WatchTblCls(document["_id"], document["userId"], document["wid"], document["name"], document["Symboles"]));
Cannot apply indexing with [] to an expression of type 'WatchTbl'
I don't understand the reason behind using WatchTbl and WatchTblCls both together. Is WatchTblCls a model for the entity WatchTbl here? Im not sure.
In any case. If you go for aggregation and want to convert WatchTbl collection to WatchTblCls list, your desired solution might look like the following. I don't know the defiitions of the classes so I'm assuming:
var client = new MongoClient("mongodb://servername:27017");
var database = client.GetDatabase("WatchTblDB");
var collectionWatchtbl = database.GetCollection<WatchTbl>("Watchtbl");
var collectionUser = database.GetCollection<UserCls>("Users");
var collectionSymbole = database.GetCollection<SymboleCls>("Users");
var list = collectionWatchtbl.AsQueryable().Select(x => new WatchTblCls() {
id = x.id,
userId = x.userId,
.....
});
If you can use the same WatchTbl class and still want to load the full collection to a local List (which is definitely not a good idea):
List<WatchTbl> list = await collectionWatchtbl.Find(x => true).ToListAsync();
I am able to insert and delete data in a RavenDB store. I am also able to run queries that return multiple documents.
I am however unable to load data using session.Load<Book>("books/0") which returns null. Additionally, I get an InvalidOperationException when I try and run a query that searches for a book with a given ID but this particular behavior is expected.
Is there anything I am missing when fetching the doc?
Code Block:
using (var session = DocumentStoreHolder.Store.OpenSession())
{
for (int i = 0; i < count; i++)
{
var doc = session.Load<Book>(i);
Console.WriteLine(doc);
}
}
Do you have a document with the id books/0?
Typically document ids start with 1, so you'll have books/1, etc.
It's been a little while since I used Raven but I believe you need to use a Query not Load.
using (var session = DocumentStoreHolder.Store.OpenSession())
{
var books = session.Query<Book>().ToList();
books.ForEach(book =>
{
//Note that book is an object, write out one of it's properties
Console.WriteLine(book.Name);
});
//or get single book:
var id = 1;
var book = session.Query<Book>()
.FirstOrDefault(x => x.ID == id);
}
I am trying to delete documents ids from a collection in RavenDB using the below logic
var documentstore = new DocumentStore
{
Url = "http://localhost:8080",
DefaultDatabase = "Employee"
};
documentstore.Initialize();
using (var session = documentstore.OpenSession())
{
var test = new List<string>();
test.Add("emps/81993");
test.Add("emps/40319");
var w1 = session.Load<Employee>(test);
session.Delete(w1);
session.SaveChanges();
}
I get the below error
Models.Employee[] is not associated with the session, cannot delete unknown
How do I go about doing a bulk delete of document Ids from the collection?
Thanks
You are trying to delete the array of employees, not each employee itself. When you pass in an Enumerable in the Load, you will get an array back containing each entity.
Try this instead:
using (var session = documentstore.OpenSession())
{
var test = new List<string>();
test.Add("emps/81993");
test.Add("emps/40319");
Employee[] employees = session.Load<Employee>(test);
foreach (var employee in employees)
{
session.Delete(employee);
}
session.SaveChanges();
}
To further explain, the returned array is not tracked by RavenDb's UoW, but each individual item in the array is, that's why you get the message about Employee[] is not associated with the session.
You can use set based operation.
The following code will query specific index and delete everything matching the query
var operation = store.DatabaseCommands.DeleteByIndex("Index Name", new IndexQuery
{
Query = "Lucene query of stuff to delete"
}, options: null);
for example, the following code will delete all documents from a document collection called "Companies" (excerpt from one of RavenDB unit tests)
var operation = documentStore.DatabaseCommands.DeleteByIndex("Raven/DocumentsByEntityName", new IndexQuery
{
Query = "Tag:[[Companies]]"
});
You can read more in this link to RavenDB documentation