Skip to content

Instantly share code, notes, and snippets.

View Eosis's full-sized avatar
🎯

Rupert Eosis

🎯
View GitHub Profile
// MeetingCodec.ts
import * as T from 'io-ts'
import BaseMeetingCodecT from '../../shared/codecs/BaseMeetingCodec'
import JustStartTimeT from './JustStartTimeCodec'
const MeetingT = T.intersection([BaseCodecT, JustStartTimeT])
export default MeetingT
// The type we get from on retrieving the document from firestore:
type FromFirestore = {
"meetingAgenda": string
"startTime": firestore.Timestamp // 😱 This is a different type between the client and the admin sdks.
}
// The type we want in in our Frontend and Backend:
type Meeting = {
meetingAgenda: string,
startTime: Luxon.DateTime
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
match /users/{userId} {
allow read: if request.auth != null
match /private/info {
allow write: if request.auth && request.auth.uid == userId
allow read: if request.auth && request.auth.uid == userId
}
}
// Collection at /users/rzJZAyMbXaeXQ9OWeIckM88DUcq1
{
"name": "Rupert", // I'm happy for people to see this
}
// Collection at /users/rzJZAyMbXaeXQ9OWeIckM88DUcq1/private/info
{
"email": "me@example.com", // I can be hidden now!
"birthday": "1970-01-01" // I can be hidden now!
}
const superSecretEmail = userDoc.data().email. // 😱
const superSecretBirthday = userDoc.data().birthday // 😱
const userDoc = await getDoc(doc(db, '/users/', uid))
const name = userDoc.data().name
// Collection at /users/rzJZAyMbXaeXQ9OWeIckM88DUcq1
{
"name": "Rupert", // I'm happy for people to see this
"email": "me@example.com", // I'd rather they didn't see this
"birthday": "1970-01-01" // I'd rather they didn't see this
}
import * as T from 'io-ts'
import BaseMeetingCodecT from '../../shared/codecs/BaseMeetingCodec'
import JustStartTimeT from './JustStartTimeCodec'
const MeetingT = T.intersection([BaseCodecT, JustStartTimeT])
export default MeetingT
// Client LuxonTimestampCodec:
import * as T from 'io-ts'
import { DateTime } from 'luxon'
import { Timestamp } from 'firebase/firestore'
const LuxonDateTimeT = new T.Type<DateTime, Timestamp, unknown>(
'LuxonDateTimeT',
(u: unknown): u is DateTime => u instanceof DateTime,
(u: unknown, c: T.Context) => {
if (!(u instanceof Timestamp)) {
// Backend TimestampCodec
import * as T from 'io-ts'
import { DateTime } from 'luxon'
import * as admin from 'firebase-admin'
export const LuxonDateTimeT = new T.Type<DateTime, admin.firestore.Timestamp, unknown>(
'LuxonDateTimeT',
(u: unknown): u is DateTime => u instanceof DateTime,
(u: unknown, c: T.Context) => {
if (!(u instanceof admin.firestore.Timestamp)) {