oaregithub / oare_mono

1 stars 0 forks source link

Periods Page: Add ability to see occurrences when clicking on the number of occurrences #1663

Open edstratford opened 1 year ago

edstratford commented 1 year ago

Also: include code that filters according to user permission.

hbludworth commented 1 year ago

As discussed, the goal for this issue is to allow for a user to click on the occurrences number next to any year, month, or week to open a dialog that shows all of the text occurrences. Before we can implement that, there will be a few things to prepare. I've outlined each of the steps below and split everything into reasonably sized pieces. If you want, you can work on this PR piece-by-piece and seek reviews at each step, or you can continue working through it as desired.

Periods Cache Filter

Before we implement the clickable text occurrences interface, we will first need to fix the periods occurrences data. In its current implementation, we forgot to account for the fact that some users do not have access to certain texts. As such, their occurrences numbers should be different when they visit the Periods page.

To fix this, we will make use of cache filters. As you know, cache filters allow for us to store an "unfinished" version of data in the cache and then apply a filter to process it after retrieval. In this case, we can store a 0 occurrence in the cache and calculate and apply occurrences in the filter. That way, they will be user-specific because they will be generated every time.

To do this, we will first remove the code that calculates occurrence numbers when retrieving the periods. As discussed we will just hardcode an initial value of 0. So, inside of the yearMaker, monthMaker, and weekMaker functions, remove the call to this.getOccurrences and simply include the value 0 in the returned Object.

Now, the cache data will simply have a 0 for all occurrences when it is next inserted.

Before we can create the cache filter, we will want to revamp the function that is used for getting the number of occurrences. It needs support for filtering out texts that a user can't see. It also should have support for optionally applying a search filter on the text names (this is because this same function will be reused from the occurrences dialog box to allow for searching. The number of texts will obviously change when a search is performed. As such, the count function needs to allow for searches).

To start, we will rename the PeriodsDao.getOccurrences function. Name it getPeriodOccurrencesCount. We also need to give it a couple more parameters. First, add a parameter called userUuid that can be string | null. We will use this to know what texts to filter out. Next, add a parameter that looks like this: pagination: Partial<Pagination> = {}. This creates an option pagination parameter, allowing us to optionally include a search filter. Specify that the function should return a Promise<number>.

We will closely model this function after the one found at PersonDao.getPersonOccurrencesCount, so you can look at that for reference. You will see that you need to use CollectionTextUtils.textsToHide to get a list of text uuids that the requesting user cannot see. From there, you should be able to see how to implement your periods count query so that it also uses textsToHide, pagination.filter, and more. It should look very similar to the queries found in PersonDao.getPersonOccurrencesCount.

Once that is complete, this function will allow us to get user-specific occurrences counts and will support search filters on that data. Pretty cool, right?

Now, we need to create the cache filter. In the backend cache folder there is a file called filters.ts. Within that file, create a new filter function called periodsFilter. You'll need to specify a type of PeriodResponse in a few places to indicate what kind of data this filter is allowed to process.

Within the filter, you'll simply map over the data you receive from the first parameter and apply occurrences to all of the years, months, and weeks using the newly created getPeriodOccurrencesCount function. Luckily, the cache filters are all configured to provide you with a user object that includes the user.uuid that you need.

Once that filter function has been created, go to your GET /periods route and update the cacheMiddleware call to use the periodsFilter instead of noFilter. Update the cache.insert call within the route to do the same.

Now, you should be able to clear the cache using Admin Settings and load the periods page. It should look exactly the same for you because you can see all texts, but if it's working, we can know that it is getting the data in a user-specific way!

Text Occurrences DAO Function

COMING SOON

Backend Routes

COMING SOON

Frontend Updates

COMING SOON