I can get a list of categories and all nested subs as well, but the only category I want to search is 'food'. What I need back is a list of subcategories for food.
Searching categories is done with: https://api.foursquare.com/v2/venues/categories?oauth_token=[auth_token]&v=20150501
Is there a known way to just search for subcategories if I provide a category id?
You're missing categoryId=... from your query. You can find the IDs here: https://developer.foursquare.com/categorytree
At the time of writing the categoryId for food is 4d4b7105d754a06374d81259
There is a danger in what I am about to suggest, but here goes.
You could create a sample app which hits https://api.foursquare.com/v2/venues/categories?oauth_token=[oAuthToken]&v=20150506, parses the json response and stuffs the results into a database. With this database populated, copy it (and necessary model files) into your real app.
Using this local category database, your app can search for just parent categories (Arts & Entertainment, Food, etc.), or just subCategories within a given parent category (brazillian restaurants, cafes, etc.), and so on.
The danger is that if Foursquare chooses to change their category data, your local source will be out of date. You will need to have a way to update your data and, of course, ensure your app handles the change(s).
Related
In an Android app I have a list of Items which consist of name and Category. Items and categories are stored in Android's SQLite database.
class Item{
Long id;
String name;
Category category;
}
class Category{
Long id;
String name;
}
User can select categories using ComboBox list shown in dialog
and then search items of selected categories by name.
List should be filtered by categories when user click "OK" button in categories dialog
and by name when user type some text in SearchView.
How to do the filtering in proper way?
I think that filtering both categories and name on every character typed in SearchView isn't good way in term of performance.
On the other hand filtering both atributes seperately produces additional list:
Full list
Items from full list filtered by categories
3: Items from previous list fitlered by name.
The other option I thought of is to query the database on SearchView text change to get desired result instead of filtering the full list.
Thanks
This is not a simple question. All developers do it differently. I suggest few things:
Make select on database only once, when user wrote first 1 or maybe 2 chars or choose category.
Remember selected from database list. Let's name it - originalList. Visible list keep on the other object like filteredList.
Use something to avoid filtering everytime. If you know what is reactive programming you can use it's features. If you want to do it in oldschool way, you can for example make a task/job for filtering, which will be canceled, when new filter order will apear. In that way you have always 0 or 1 ongoing filtering.
It doesn't matter how many data is needed for filtering if your query is processes by one task/job. It has to also be able to work with null attributes if nothing is set for category or name.
When user added new requirement - filter filteredList for optimization.
Remember that, when you are clearing the letters - the list has to also change. This time you have no choice and has to filter originalList or make select on database.
But this is the most complicated way, which is used, when the list of item's can be very big. Otherwise you can simply select all of objects from the table in SQLite database as an oryginal list and work on it latter in the Java code.
The way of doing it depends from environemt so number of items, number of columns, lenght of the names etc. Try to find a way suitable to tour situation - I am sure, there is many articles in the network about it.
I have an application where members can post content, but then I have a problem. My problem is that I want to do an activity where the publications of only the author member are shown but Firestore asks me to create an Index to do this, the problem is that the document of each member is based on its UID.
For example:
My UID is: x54asdASD544
Then I try to make this query:
Query query = mMembersDB.document("POST").collection("x54asdASD544").whereEqualTo("type", "public").orderBy("date");
That's when Firestore asks me to create an index, then I create it and it works perfect after creating the index, but if I'm going to do the same, to see the publications of another author, then he asks me to create another index.
For example:
Query query = mMembersDB.document("POST").collection("x54assds").whereEqualTo("type", "public").orderBy("date");
The UID changed, then the previously created index does not work anymore.
Any solution to be able to repair this?
Any way to create indexes automatically?
Each uniquely named collection and subcollection must have its own indexes. You can't share index definitions between collections. They must be defined separately. There is no way to automatically create indexes.
Naming a subcollection based on a UID doesn't sound like a very effective way to model your data. Consider putting all the documents in one collection, put the UID as a field to those documents, and use the UID as a filter to find what you want.
Is it possible to search for an unknown collection that contains a document with identifying fields like an email?
My structure is like this:
Each user gets their own collection based on a unique ID. Each collection contains a user doc and a accounts doc. User doc contains the information about the user that I would like to search for. Accounts doc contains a collection of bank accounts that I want to transfer money between users.
My problem is that I don't want users to type in the long unique id to enter the collection but to type the email of the user that is inside the collection\user document. The email is unique.
Have I just made a bad structure for my project or is there something I can do?
UPDATE
Thanks, Alex and Frank for the feedback.
I went on and changed my structure to as shown:
/users/$uid/accounts/$accountid.
Did a java Query collectionReference = db.collection("users").whereEqualTo("uEmail", userEmail); and saving the document.getId() as a String userId.
I Then use the UserId in a spinner to enable the user to pick an account from the userId accounts collection.
As Alex said, there is no way to load data from a collection (with the client-side SDKs) unless you know the collection name.
But in this case, it seems like your collections are named after the user's UID.
That means that if the user is signed in, you can know their collection by:
String uid = FirebaseAuth.getInstance().getCurrentUser().getUid();
CollectionReference userCollection = FirebaseFirestore.getInstance().collection(uid);
A few notes:
It is much more idiomatic to store your structure with a top-level collection of users, and then a document for each user under that, and then subcollections for the other data under that. So for example: /users/$uid/accounts/$accountid.
The server-side SDKs do have a method to get a list of collections, for example like this listCollections method in the Node.js SDK. But these SDKs are only to be used in a trusted environment, such as your development machine, a server you control, or Cloud Functions, and not directly on the client. Even with this SDK though, you'll have to iterate the list of collections and check each in turn, because as said before: you can only read data from a collection of which you know the name.
If you're trying to look up the collection/UID for another user than the one who's signed in to the app, you may need to way to map an email address to a UID. Such functionality is not available in the client-side SDKs. But similar as the point above, there is a method getUserByEmail in the Admin SDKs.
Is it possible to search for an unknown collection that contains a document with identifying fields like an email?
No, you should know the name of your collection in order to be able to use it in your reference. There are no wildcards in Cloud Firestore paths to collections/documents. You have to identify every collection and every document by their specific ids.
I would like to add products to cart on the fly. This means the products to add are not stored in the database and doesn't have to. But when I take a look into the cart endpoint how items added to an order the class org.broadleafcommerce.core.order.service.call.OrderItemRequestDTO requires a product id.
So this means I've to override blCatalogService which would allow temporary products too? Is this all or did I forget something else to achieve the adding of products to the cart/order on the fly?
The OrderItem data model and services don't strictly require a SKU but many of the out of box examples do.
You should be able to override the CartEndpoint and instead of creating an OrderItemRequestDTO, create a NonDiscreteOrderItemRequestDTO.
The AddOrderItemActivity which is part of the workflow executed when an item is added checks for this type and will create an OrderItem instead of a DiscreteOrderItem or BundleOrderItem (both of which require a SKU).
Hope this helps,
Brian
Note : I work for Broadleaf
I am developing an Android app which needs to know when a contact is added/updated/deleted.
So I read several posts for it. I understand that we can get notified through Content observers whenever a contacts gets changed, but we can't get which contacts have been added/updated/deleted. So I have read the official APIs and prepared my design how to capture that particular contact.
So what I thought at the start
We will store all the contact IDs, deleted flag and version
Whenever contacts get changed I will get my table's row count and row count from Android's system.
If my rowcount is less than systems row count then a contact has been deleted.
If my rowcount is greater than systems row count then a contact has been added.
And if these are not the cases then one of the contacts version has been changed.
I have also learned that Android doesn't delete the contact if it is deleted by user, but it sets 0 on deleted flag. So in these cases the row count will be same.
Android also changes the row ID of a contact many times as stated in the official docs. So how can we uniquely identify them like lookup uri and if not then we have to put observer for that also.
So I want to know whether the above is correct? And in the case a contact is added will it be added to the last row of cursor or not means if I check the last row of system database for contacts will it give me the contact added or not.
Let me explain as much as I could. Basically your policy looks pretty good, but actually it is bit more complex than you thought.
On Android, a contact can be associated with several raw contacts, which may be provided from many data providers, such as Google, Facebook, Skype and so on. For example, if one of your friends in your local contacts is also using Skype, there are two raw contacts existing separately in ContactContracts.RawContacts, but they will be aggregated automatically and show up just as one contact when you query to ContactsContract.Contacts.
That is also why it's hard to identify a contact uniquely, because you can split or join them anytime you want. LOOKUP_KEY isn't very handy for this case.
Many apps except Google only provide a one-way sync, i.e. only from service to contacts, so they are read-only. In this case, the deleted flag will not be used and simply deleted during their synchronization process. Thus, you can not simply rely on the flag.
Though there isn't a good simple solution, I guess it's much easier to achieve what you want, if you observe for a specific RawContacts, not Contacts. Hope this helps your understanding.
I think the best practice is to monitoring whenever a contact has aggregate to another one and identify them by the contactName, not the _ID or CONTACT_ID.
Take a look at this possibly contacts operations:
Insert
A Contact cannot be created explicitly. When a raw contact is inserted, the provider will first try to find a Contact representing the same person. If one is found, the raw contact's CONTACT_ID column gets the _ID of the aggregate Contact. If no match is found, the provider automatically inserts a new Contact and puts its _ID into the CONTACT_ID column of the newly inserted raw contact.
Update
Only certain columns of Contact are modifiable: TIMES_CONTACTED, LAST_TIME_CONTACTED, STARRED, CUSTOM_RINGTONE, SEND_TO_VOICEMAIL. Changing any of these columns on the Contact also changes them on all constituent raw contacts.
Delete
Be careful with deleting Contacts! Deleting an aggregate contact deletes all constituent raw contacts. The corresponding sync adapters will notice the deletions of their respective raw contacts and remove them from their back end storage.
Query
If you need to read an individual contact, consider using CONTENT_LOOKUP_URI instead of CONTENT_URI.
If you need to look up a contact by the phone number, use PhoneLookup.CONTENT_FILTER_URI, which is optimized for this purpose.
If you need to look up a contact by partial name, e.g. to produce filter-as-you-type suggestions, use the CONTENT_FILTER_URI URI.
If you need to look up a contact by some data element like email address, nickname, etc, use a query against the ContactsContract.Data table. The result will contain contact ID, name etc.
The problem, though, is that you could have two 'Phillip Morris' in your contact list that aren't the same person.
For further information, see this section of Android Classes Documentation.