Replies: 3 comments
-
How we control this cache invalidation?
Idempotent methods: Maybe a simple memoization help even if isn't same lambda instance used, to reduce resource usage and speed up response when possible. // laconia internal code
const memoize = (storage = new Map()) => fn => async (event, laconiaContext) => {
if (await storage.has(event, laconiaContext))
return storage.get(event, laconiaContext);
const value = await fn(event, laconiaContext);
await storage.set(event, value, laconiaContext);
return value;
};
const sharedMap = new Map();
const memoizator = (
hash = event => event,
map = () => sharedMap
) => memoize({
has: (event, laconiaContext) => map(laconiaContext).has(hash(event)),
get: (event, laconiaContext) => map(laconiaContext).get(hash(event)),
set: (event, value, laconiaContext) => map(laconiaContext).set(hash(event), value)
}) // user code
// these two are almost the same;
let memoizationAdapter = memoize();
memoizationAdapter = memoizator();
// use body.id as hash function
// and laconiaContext.redis as cache
memoizationAdapter = memoize({
has: ({ id }, { redis }) => redis.has(id),
get: ({ id }, { redis }) => redis.get(id),
set: ({ id }, value, { redis } => redis.set(id, value)
});
// is the same as
memoizationAdapter = memoizator(
({ id }) => id,
({ redis }) => redis
);
const apiAdapter = apigateway({ inputType: "body" }).;
const app = body => console.log(JSON.stringify(body));
exports.handler = laconia(apiAdapter(memoizationAdapter(app))))
.register('redis', () => new Map()); Non-idempotent methods: If we use same approach as before, it could fail to be idempotent when second call try to search in cache before first request fills it. To solve this problem my solution was introduce a queue (SQS) with delay.
This is over engineering and may isn't fail proof. A better solution would use websocket and only answer request at 7, but I'm afraid of api gateway price and browser compatibility |
Beta Was this translation helpful? Give feedback.
-
Hey @hugosenari. That's an interesting solution. I could see that Laconia can implement the I think it's worth separating the use case for idempotency and caching though. I'd like to see your scenario as more towards caching. There are multiple caching strategies, one is by time. If the last time the cache is stored is 5 minutes ago, we could purge it. Most of the times though, I managed to survive with AWS caches, such as API Gateway cache (it's quite pricey, but at least I don't need to manage anymore infrastructure). What's your use case at the moment to not use cache like AWS Gateway cache? The use case that I have in mind though, is something different. The use case is more towards making "non-idempotent" operation be "idempotent" easily. The ideal solution is of course to make everything that you're trying to do idempotent, but sometimes this is not achievable. For example, if we have a Lambda that sends an e-mail to a customer, we really don't want the Lambda to accidentally be triggered twice! In that scenario, I would start to store the record in DynamoDB to make sure that I'm not sending the e-mail again. My lambda, in this case, is being triggered with 'async' event type, which means it might be triggered twice. |
Beta Was this translation helpful? Give feedback.
-
came across this while searching around for a general solution to this problem. a month or so ago it looks like aws-labs released a relatively standardized approach for this in open source. Theres a python version but not sure if one also exists for javscript, but either way, it could be helpful inspiration if you are looking to solve the same issue generally. https://awslabs.github.io/aws-lambda-powertools-python/api/utilities/idempotency/index.html |
Beta Was this translation helpful? Give feedback.
-
When building on a serverless architecture, it is very common for me to find that I need to make AWS Lambda execution idempotent. This can happen due to various reasons such as error retries, or due to at-least-once delivery event trigger.
Discussion
Beta Was this translation helpful? Give feedback.
All reactions