Caching Components Per Key

If you need to cache a component per unique identifier, you can use the CachedPerKey functions.

These functions allow you to cache a component by a specific key. This key can be any string that uniquely identifies the user.

Note: I'm using the term 'user' to simply mean a unique identifier. This could be a user ID, session ID, or any other unique identifier.

Methods for caching per key:

Copy
 1// No arguments passed to the component, the component can be cached by a specific key
 2h.CachedPerKey(duration time.Duration, cb GetElementFuncWithKey)
 3// One argument passed to the component, the component can be cached by a specific key
 4h.CachedPerKeyT1(duration time.Duration, cb GetElementFuncWithKey)
 5// Two argument passed to the component, the component can be cached by a specific key
 6h.CachedPerKeyT2(duration time.Duration, cb GetElementFuncWithKey)
 7// Three arguments passed to the component, the component can be cached by a specific key
 8h.CachedPerKeyT3(duration time.Duration, cb GetElementFuncWithKey)
 9// Four arguments passed to the component, the component can be cached by a specific key
10h.CachedPerKeyT4(duration time.Duration, cb GetElementFuncWithKey)

Usage:

Copy
 1var CachedUserDocuments = h.CachedPerKeyT(time.Minute*15, func(ctx *h.RequestContext) (string, h.GetElementFunc) {
 2	userId := getUserIdFromSession(ctx)
 3	return userId, func() *h.Element {
 4		return UserDocuments(ctx)
 5	}
 6})
 7
 8func UserDocuments(ctx *h.RequestContext) *h.Element {
 9	docService := NewDocumentService(ctx)
10	// Expensive call
11	docs := docService.getDocuments()
12	return h.Div(
13		h.Class("grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4"),
14		h.List(docs, func(doc Document, index int) *h.Element {
15			return h.Div(
16				h.Class("p-4 bg-white border border-gray-200 rounded-md"),
17				h.H3(doc.Title),
18				h.P(doc.Description),
19			)
20		}),
21	)
22}
23
24func MyPage(ctx *h.RequestContext) *h.Page {
25	
26	// Note this is not a real way to create a context, just an example
27	user1 := &h.RequestContext{
28		Session: "user_1_session",
29    }
30	
31	user2 := &h.RequestContext{
32		Session: "user_2_session",
33	}
34	
35	// Different users will get different cached components
36    return h.NewPage(
37        CachedUserDocuments(user1),
38        CachedUserDocuments(user2),
39    )
40}

We are using CachedPerKeyT because the component takes one argument, the RequestContext.

If the component takes more arguments, use CachedPerKeyT2, CachedPerKeyT3, etc.

Important Note:

The cached value is stored globally in memory by key, it is shared across all requests. Ensure if you are storing request-specific data in a cached component, you are using a unique key for each user.

The arguments passed into cached component DO NOT affect the cache key. The only thing that affects the cache key is the key returned by the GetElementFuncWithKey function.

Ensure the declaration of the cached component is outside the function that uses it. This is to prevent the component from being redeclared on each request.