-- ============================================================================
-- Signal Protocol Schema Updates
-- ============================================================================
-- Updates to support proper Signal Protocol implementation with separate
-- one_time_prekeys table and profiles identity key storage.
-- ============================================================================

-- ============================================================================
-- 1. Update profiles table to store identity key and registration ID
-- ============================================================================

-- Add Signal Protocol identity key and registration ID to profiles
ALTER TABLE profiles
ADD COLUMN IF NOT EXISTS identity_key TEXT,
ADD COLUMN IF NOT EXISTS registration_id INTEGER;

-- ============================================================================
-- 2. Create separate one_time_prekeys table
-- ============================================================================

-- Separate table for one-time pre-keys (consumed on use)
CREATE TABLE IF NOT EXISTS one_time_prekeys (
    id SERIAL PRIMARY KEY,
    user_id UUID NOT NULL REFERENCES profiles(id) ON DELETE CASCADE,
    key_id INTEGER NOT NULL,
    public_key TEXT NOT NULL,
    created_at TIMESTAMPTZ DEFAULT NOW(),

    -- Ensure unique key_id per user
    UNIQUE(user_id, key_id)
);

-- Index for efficient key consumption
CREATE INDEX IF NOT EXISTS idx_one_time_prekeys_user_id ON one_time_prekeys(user_id);

-- ============================================================================
-- 3. Update signal_keys table structure
-- ============================================================================

-- Remove one_time_prekeys from signal_keys (now separate table)
ALTER TABLE signal_keys
DROP COLUMN IF EXISTS one_time_prekeys;

-- Add registration_id to signal_keys if not already present
ALTER TABLE signal_keys
ADD COLUMN IF NOT EXISTS registration_id INTEGER;

-- ============================================================================
-- 4. Update consume_one_time_prekey function
-- ============================================================================

-- Update the function to work with the separate table
CREATE OR REPLACE FUNCTION consume_one_time_prekey(target_user_id UUID)
RETURNS TABLE(key_id INTEGER, public_key TEXT) AS $$
BEGIN
    RETURN QUERY
    DELETE FROM one_time_prekeys
    WHERE user_id = target_user_id
    ORDER BY created_at ASC
    LIMIT 1
    RETURNING one_time_prekeys.key_id, one_time_prekeys.public_key;
END;
$$ LANGUAGE plpgsql SECURITY DEFINER;

-- ============================================================================
-- 5. Update RLS policies for one_time_prekeys
-- ============================================================================

-- Enable RLS
ALTER TABLE one_time_prekeys ENABLE ROW LEVEL SECURITY;

-- Users can read their own pre-keys (for management)
CREATE POLICY one_time_prekeys_select_own ON one_time_prekeys
    FOR SELECT USING (auth.uid() = user_id);

-- Users can insert their own pre-keys
CREATE POLICY one_time_prekeys_insert_own ON one_time_prekeys
    FOR INSERT WITH CHECK (auth.uid() = user_id);

-- Users can delete their own pre-keys (when consumed)
CREATE POLICY one_time_prekeys_delete_own ON one_time_prekeys
    FOR DELETE USING (auth.uid() = user_id);

-- ============================================================================
-- 6. Migration helper: Move existing one_time_prekeys to new table
-- ============================================================================

-- Insert existing one_time_prekeys from signal_keys into the new table
INSERT INTO one_time_prekeys (user_id, key_id, public_key)
SELECT
    sk.user_id,
    (prekey->>'id')::INTEGER,
    prekey->>'key'
FROM signal_keys sk,
     jsonb_array_elements(sk.one_time_prekeys) AS prekey
ON CONFLICT (user_id, key_id) DO NOTHING;

-- Remove the old column after migration
-- (Commented out to prevent accidental data loss - run manually after verification)
-- ALTER TABLE signal_keys DROP COLUMN IF EXISTS one_time_prekeys;

-- ============================================================================
-- 7. Comments for documentation
-- ============================================================================

COMMENT ON TABLE one_time_prekeys IS 'One-time pre-keys for Signal Protocol. Each key is consumed after first use.';
COMMENT ON COLUMN profiles.identity_key IS 'Signal Protocol identity key public part (base64 encoded)';
COMMENT ON COLUMN profiles.registration_id IS 'Signal Protocol registration ID for this user';
COMMENT ON FUNCTION consume_one_time_prekey IS 'Atomically consumes and returns the oldest one-time pre-key for a user';
