One of the main features of HadCoffee is keeping a list of your favourite cafes and the ones you want to try. Favs are useful when people ask for recommendations and you’re at risk of forgetting those dearest to you.
To Try is a good way to bookmark cafes to visit when you’re near them later.
Cafes can be added and removed from these lists with their UI controls. Initially these were only present on the cafe detail page, but over time I have included them on the search results listing and on the Cafes page.
To correctly show the status (i.e. whether a cafe is already on either of these lists) I needed to rebuild the local state to use Vuex. This means the icons can be rendered in multiple locations of the UI and show synced state. It also makes it far easier to deploy them in new UI sections later.
To support that data structure though I needed to do a refactor of the backend API which provides that data from the server. The API can be used to both list just the cafe ids for each list, or return more fleshed out object data for the features that render more complete cafe information.
I’m happy with this final design. I can now place these controls wherever they need to go on the UI and they’ll initiate with state from the server, then manage it locally through Vuex. As a bonus you get a nice little page load animation with the star filling up and the list clicking on if the cafe is active on the list.
The home screen will let you search for cafes, either by location, or by cafe name (or the combination of the two).
Today I made good progress with the frontend flow of data to support this feature. The app uses Vuex for state storage. This feature has three different Vue components accessing related data to manage the users search.
The quick location search will use the browser geolocation feature as a default, and that data will flow through to the search form via Vuex. If the user is searching for a cafe by name that content will also go through Vuex for global access.
When the search event is triggered the results component can access this state, and send the API request to the server and build out the result set.
The event listening process was a little tricky, as state properties are accessed via getters, and so the normal method of capturing events and passing to component properties won’t work. A combination of Vuex getters, computed properties and watchers lets the result component listen for the search action to do its work.
I can now work on the backend logic for the API endpoint and build out the results data.
I’m a little concerned that that work could get heavy as this is almost a mini-SPA now. Possibly Livewire would have been a good solution, but I’m not going to introduce new architecture at this point in the project development.
I may have to consider how to cache the search result if the user navigates away and comes back. I’d prefer to avoid having to refetch from the server as that delay is annoying when it’s data you have already accessed. Worst case scenario I guess is to capture search criteria in localStorage, and cache the result server side so the response comes in <100ms.