Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

c# Query path for Firebase data through FirebaseDatabase.net

I'm having trouble figuring out how to query for a 3rd parties data. Here's how it's structured

/bucketa/bucketb/bucketc/someguidtypekey/anotherguidtypekey/(fields I want to map here)

I've tried this:

var stats = await firebase.Child("bucketa/bucketb/bucketc").OnceAsync<WrapperClass>();

Where WrapperClass is a Key/Object combo, then THAT object is another Key/Object combo, and then that object is the actual class.

public class WrapperClass
{
    public string Key { get; set; }
    public WrapperClass2 Stats { get; set; }
}

public class WrapperClass2
{
    public string Key { get; set; }
    public RealClass Stats { get; set; }
}

public class RealClass
{
    public string Field1 { get; set; }
    public string Field2 { get; set; }
    public string Field3 { get; set; }
    public string Field4 { get; set; }
}

I've also tried:

var stats = await firebase.Child("bucketa/bucketb/bucketc/*/*").OnceAsync<RealClass>();

But that just returned a string of the object type.

Can anyone help out here?

This is in C#, using FirebaseDatabase.net

Edit:

All right, now we are getting closer. Implementing @ElmarJensen fix (from one of his comments):

...OnceAsync<Dictionary<string, Dictionary<string, RealClass>>>();

I'm now getting the error:

Error converting value True to type 'RealClass'

In the error, it says it's trying to convert RealClass.property1 where property1 is of type bool.

Why is it trying to convert the property1 to my RealClass object type instead of the parent object? The structure makes sense to me. And in the exception, the "responseData" property has all of the records that I expected in the correct JSON format, so not sure what's going on here.

Edit 2: Here's the actual data format:

{
    "0M6bRFLLokR6sIJAcKFN6y91NXB3": {
        "-KYdDf62eQUMGb-ov737": {
            "somethingBoolean":true,
            "asdf":"Joe User",
            "oasdfasdfsad": {
                "firstName":"asdf",
                "lastName":"asdfasdf",
                "tasdfme":"Wasdfh",
                "teasdfore":6,
                "teaasdfme":"SDFO"
            },
            "fasdfewaef":0,
            "startedAt":1.481381640492956E9,
            "updatedAt":1.481381687802693E9,
            "wfefeaefw":"182",
            "asdf": {
                "firstName":"asdf",
                "lastName":"asdf",
                "asdf":"asdfasdfasdf",
                "teamScore":0,
                "asefeawfawef":"DFDFSWEF"
            },
            "aefawefawefawefawef":0
        }
    }
}
like image 808
ganders Avatar asked Jul 06 '17 05:07

ganders


People also ask

What C is used for?

C programming language is a machine-independent programming language that is mainly used to create many types of applications and operating systems such as Windows, and other complicated programs such as the Oracle database, Git, Python interpreter, and games and is considered a programming foundation in the process of ...

What is the full name of C?

In the real sense it has no meaning or full form. It was developed by Dennis Ritchie and Ken Thompson at AT&T bell Lab. First, they used to call it as B language then later they made some improvement into it and renamed it as C and its superscript as C++ which was invented by Dr.

What is C in C language?

What is C? C is a general-purpose programming language created by Dennis Ritchie at the Bell Laboratories in 1972. It is a very popular language, despite being old. C is strongly associated with UNIX, as it was developed to write the UNIX operating system.

Is C language easy?

C is a general-purpose language that most programmers learn before moving on to more complex languages. From Unix and Windows to Tic Tac Toe and Photoshop, several of the most commonly used applications today have been built on C. It is easy to learn because: A simple syntax with only 32 keywords.


1 Answers

Wildcards ("bucketa/bucketb/bucketc/*/*") do not exist like that in Firebase, so if you have no influence on the datastructure, you're stuck with downloading the full data tree at once from the root at "bucketa/bucketb/bucketc". The problem is that for firebase-database-dotnet, the "children" of this tree (someguidtypekey/anotherguidtypekey) will appear as properties of the object with the GUIDkey as the property name - which means that you need to know the guidkeys at compile time for this to work. However, given that the method uses JSON.net under the hood, and that library supports deserializing into Dictionaries instead of objects as well, the following may actually work:

await firebase.Child("bucketa/bucketb/bucketc").OnceAsync<Dictiona‌​ry<string, Dictionary<string, RealCl‌​ass>>>();

Also, if it is only one query, it would be fairly easy to do this "manually" with a HttpClient, or use FireSharp (another FB .net library, https://github.com/ziyasal/FireSharp) that allows you easy direct access to the "raw" returned JSON, like this:

FirebaseResponse response = await client.GetAsync("bucketa/bucketb/bucketc");
var myJson = response.Body;

After that, you can easily iterate the properties of the returned json object (e.g. Iterating over JSON object in C#).

Of course, if you had direct control over the datastructure, the advise would be to further flatten it (see https://firebase.google.com/docs/database/android/structure-data).

I am not entirely sure what you mean by "But that just returned a string of the object type." .OnceAsync<RealClass>(); will return a collection of objects of type FirebaseObject (the original object is exposed as its Object property) - never a String.

Reply to update

It sounds as if your query goes one layer deeper than I assumed from you data description. Would this work?

await firebase.Child("bucketa/bucketb/bucketc").OnceAsync<Dictiona‌​ry<string, RealCl‌​ass>>();
like image 62
Elmar Jansen Avatar answered Sep 20 '22 14:09

Elmar Jansen