From 8ae56a8df63171c9077733b7d6a40f3070084391 Mon Sep 17 00:00:00 2001 From: timurgordon Date: Sun, 9 Feb 2025 17:53:16 +0000 Subject: [PATCH] new --- lib/clients/livekit/access_token.v | 153 ++++++++++++++ lib/clients/livekit/server_client.v | 199 +++++++++++++++++++ lib/security/authentication/backend_memory.v | 38 ++++ 3 files changed, 390 insertions(+) create mode 100644 lib/clients/livekit/access_token.v create mode 100644 lib/clients/livekit/server_client.v create mode 100644 lib/security/authentication/backend_memory.v diff --git a/lib/clients/livekit/access_token.v b/lib/clients/livekit/access_token.v new file mode 100644 index 00000000..c1fe4f50 --- /dev/null +++ b/lib/clients/livekit/access_token.v @@ -0,0 +1,153 @@ +module livekit + +// import time +// import rand +// import crypto.hmac +// import crypto.sha256 +// import encoding.base64 +// import json + +// // Define AccessTokenOptions struct +// pub struct AccessTokenOptions { +// pub mut: +// ttl int | string // TTL in seconds or a time span (e.g., '2d', '5h') +// name string // Display name for the participant +// identity string // Identity of the user +// metadata string // Custom metadata to be passed to participants +// } + +// // Struct representing grants +// pub struct ClaimGrants { +// pub mut: +// video VideoGrant +// iss string +// exp i64 +// nbf int +// sub string +// name string +// } + +// // VideoGrant struct placeholder +// pub struct VideoGrant { +// pub mut: +// room string +// room_join bool @[json: 'roomJoin'] +// can_publish bool @[json: 'canPublish'] +// can_publish_data bool @[json: 'canPublishData'] +// can_subscribe bool @[json: 'canSubscribe'] +// } + +// // SIPGrant struct placeholder +// struct SIPGrant {} + +// // AccessToken class +// pub struct AccessToken { +// mut: +// api_key string +// api_secret string +// grants ClaimGrants +// identity string +// ttl int | string +// } + +// // Constructor for AccessToken +// pub fn new_access_token(api_key string, api_secret string, options AccessTokenOptions) !AccessToken { +// if api_key == '' || api_secret == '' { +// return error('API key and API secret must be set') +// } + +// ttl := if options.ttl is int { options.ttl } else { 21600 } // Default TTL of 6 hours (21600 seconds) + +// return AccessToken{ +// api_key: api_key +// api_secret: api_secret +// identity: options.identity +// ttl: ttl +// grants: ClaimGrants{ +// exp: time.now().unix()+ttl +// iss: api_key +// sub: options.name +// name: options.name +// } +// } +// } + +// // Method to add a video grant to the token +// pub fn (mut token AccessToken) add_video_grant(grant VideoGrant) { +// token.grants.video = grant +// } + + +// // Method to generate a JWT token +// pub fn (token AccessToken) to_jwt() !string { +// // Create JWT payload +// payload := json.encode(token.grants) + +// println('payload: ${payload}') + +// // Create JWT header +// header := '{"alg":"HS256","typ":"JWT"}' + +// // Encode header and payload in base64 +// header_encoded := base64.url_encode_str(header) +// payload_encoded := base64.url_encode_str(payload) + +// // Create the unsigned token +// unsigned_token := '${header_encoded}.${payload_encoded}' + +// // Create the HMAC-SHA256 signature +// signature := hmac.new(token.api_secret.bytes(), unsigned_token.bytes(), sha256.sum, sha256.block_size) + +// // Encode the signature in base64 +// signature_encoded := base64.url_encode(signature) + +// // Create the final JWT +// jwt := '${unsigned_token}.${signature_encoded}' +// return jwt +// } + +// // TokenVerifier class +// pub struct TokenVerifier { +// api_key string +// api_secret string +// } + +// // Constructor for TokenVerifier +// pub fn new_token_verifier(api_key string, api_secret string) !TokenVerifier { +// if api_key == '' || api_secret == '' { +// return error('API key and API secret must be set') +// } +// return TokenVerifier{ +// api_key: api_key +// api_secret: api_secret +// } +// } + +// // Method to verify the JWT token +// pub fn (verifier TokenVerifier) verify(token string) !ClaimGrants { +// // Split the token into parts +// parts := token.split('.') +// if parts.len != 3 { +// return error('Invalid token') +// } + +// // Decode header, payload, and signature +// payload_encoded := parts[1] +// signature_encoded := parts[2] + +// // Recompute the HMAC-SHA256 signature +// unsigned_token := '${parts[0]}.${parts[1]}' +// expected_signature := hmac.new(verifier.api_secret.bytes(), unsigned_token.bytes(), sha256.sum, sha256.block_size) +// expected_signature_encoded := base64.url_encode(expected_signature) + +// // Verify the signature +// if signature_encoded != expected_signature_encoded { +// return error('Invalid token signature') +// } + +// // Decode the payload +// payload_json := base64.url_decode_str(payload_encoded) + +// // Parse and return the claims as ClaimGrants +// return json.decode(ClaimGrants, payload_json) +// } \ No newline at end of file diff --git a/lib/clients/livekit/server_client.v b/lib/clients/livekit/server_client.v new file mode 100644 index 00000000..edaf1f1c --- /dev/null +++ b/lib/clients/livekit/server_client.v @@ -0,0 +1,199 @@ +module livekit + +import net.http +import json + +// // pub struct Client { +// // pub: +// // host string +// // token string +// // } + +// // pub struct Room { +// // pub mut: +// // sid string +// // name string +// // empty_timeout string +// // max_participants string +// // creation_time string +// // turn_password string +// // metadata string +// // num_participants u32 +// // active_recording bool +// // } + +// pub struct ParticipantInfo { +// pub mut: +// sid string +// identity string +// name string +// state string +// tracks []TrackInfo +// metadata string +// joined_at i64 +// permission ParticipantPermission +// is_publisher bool +// } + +// pub struct TrackInfo { +// pub mut: +// sid string +// typ string @[json: 'type'] +// source string +// name string +// mime_type string +// muted bool +// width u32 +// height u32 +// simulcast bool +// disable_dtx bool +// layers []VideoLayer +// } + +// pub struct ParticipantPermission { +// pub mut: +// can_subscribe bool +// can_publish bool +// can_publish_data bool +// } + +// pub struct VideoLayer { +// pub mut: +// quality string +// width u32 +// height u32 +// } + +// // Helper method to make POST requests to LiveKit API +// fn (client Client) make_post_request(url string, body string) !http.Response { +// mut headers := http.new_header() +// headers.add_custom('Authorization', 'Bearer ${client.token}')! +// headers.add_custom('Content-Type', 'application/json')! + +// req := http.Request{ +// method: http.Method.post +// url: url +// data: body +// header: headers +// } +// return req.do()! +// } + +// pub struct CreateRoomArgs { +// pub: +// name string +// empty_timeout u32 +// max_participants u32 +// metadata string +// } + +// // RoomService API methods +// pub fn (client Client) create_room(args CreateRoomArgs) !Room { +// body := json.encode(args) +// url := '${client.host}/twirp/livekit.RoomService/CreateRoom' +// response := client.make_post_request(url, body)! + +// return json.decode(Room, response.body)! +// } + +// // pub fn (client Client) list_rooms(names []string) ![]Room { +// // body := json.encode({ +// // 'names': names +// // }) +// // url := '${client.host}/twirp/livekit.RoomService/ListRooms' +// // response := client.make_post_request(url, body)! + +// // return json.decode([]Room, response.body)! +// // } + +// pub fn (client Client) delete_room(room_name string) ! { +// body := json.encode({ +// 'room': room_name +// }) +// url := '${client.host}/twirp/livekit.RoomService/DeleteRoom' +// _ := client.make_post_request(url, body)! +// } + +// pub fn (client Client) list_participants(room_name string) ![]ParticipantInfo { +// body := json.encode({ +// 'room': room_name +// }) +// url := '${client.host}/twirp/livekit.RoomService/ListParticipants' +// response := client.make_post_request(url, body)! + +// return json.decode([]ParticipantInfo, response.body)! +// } + +// pub fn (client Client) get_participant(room_name string, identity string) !ParticipantInfo { +// body := json.encode({ +// 'room': room_name +// 'identity': identity +// }) +// url := '${client.host}/twirp/livekit.RoomService/GetParticipant' +// response := client.make_post_request(url, body)! + +// return json.decode(ParticipantInfo, response.body)! +// } + +// pub fn (client Client) remove_participant(room_name string, identity string) ! { +// body := json.encode({ +// 'room': room_name +// 'identity': identity +// }) +// url := '${client.host}/twirp/livekit.RoomService/RemoveParticipant' +// _ := client.make_post_request(url, body)! +// } + +// pub struct MutePublishedTrackArgs { +// pub: +// room_name string +// identity string +// track_sid string +// muted bool +// } + +// pub fn (client Client) mute_published_track(args MutePublishedTrackArgs) ! { +// body := json.encode(args) +// url := '${client.host}/twirp/livekit.RoomService/MutePublishedTrack' +// _ := client.make_post_request(url, body)! +// } + +// pub struct UpdateParticipantArgs { +// pub: +// room_name string @[json: 'room'] +// identity string +// metadata string +// permission ParticipantPermission +// } + +// pub fn (client Client) update_participant(args UpdateParticipantArgs) ! { +// body := json.encode(args) +// url := '${client.host}/twirp/livekit.RoomService/UpdateParticipant' +// _ := client.make_post_request(url, body)! +// } + +// pub struct UpdateRoomMetadataArgs { +// pub: +// room_name string @[json: 'room'] +// metadata string +// } + +// pub fn (client Client) update_room_metadata(args UpdateRoomMetadataArgs) ! { +// body := json.encode(args) +// url := '${client.host}/twirp/livekit.RoomService/UpdateRoomMetadata' +// _ := client.make_post_request(url, body)! +// } + +// pub struct SendDataArgs { +// pub: +// room_name string @[json: 'room'] +// data []u8 +// kind string +// destination_identities []string +// } + +// pub fn (client Client) send_data(args SendDataArgs) ! { +// body := json.encode(args) +// url := '${client.host}/twirp/livekit.RoomService/SendData' +// _ := client.make_post_request(url, body)! +// } diff --git a/lib/security/authentication/backend_memory.v b/lib/security/authentication/backend_memory.v new file mode 100644 index 00000000..510c7e6c --- /dev/null +++ b/lib/security/authentication/backend_memory.v @@ -0,0 +1,38 @@ +module authentication + +import log + +// // Creates and updates, authenticates email authentication sessions +// @[noinit] +// struct MemoryBackend { +// mut: +// sessions map[string]AuthSession +// logger &log.Logger = &log.Logger(&log.Log{ +// level: .info +// }) +// } + +// // factory for +// pub fn new_memory_backend() !MemoryBackend { +// return MemoryBackend{} +// } + +// fn (mut backend MemoryBackend) create_auth_session(session AuthSession) ! { +// backend.sessions[session.email] = session +// } + +// fn (backend MemoryBackend) read_auth_session(email string) ?AuthSession { +// return backend.sessions[email] or { return none } +// } + +// fn (mut backend MemoryBackend) update_auth_session(session AuthSession) ! { +// backend.sessions[session.email] = session +// } + +// fn (mut backend MemoryBackend) set_session_authenticated(email string) ! { +// backend.sessions[email].authenticated = true +// } + +// fn (mut backend MemoryBackend) delete_auth_session(email string) ! { +// backend.sessions.delete(email) +// }