def lambda_handler()

in lca-ai-stack/source/lambda_functions/merge_recording_audio/merge_recording_audio.py [0:0]


def lambda_handler(event, context):  # pylint: disable=unused-argument
    """Lambda handler"""
    # pylint: disable=too-many-locals
    logger.info("Processing audio merge request event >>>")
    logger.info(event)
    try:
        for s3event in event["Records"]:
            event_body = json.loads(s3event["body"])
            if event_body.get("Records") is None:
                logger.info("Skipping unexpected record:")
                logger.info(event_body)
                continue
            for record in event_body["Records"]:
                recording_bucket = record.get("s3", {}).get("bucket", {}).get("name", {})
                call_id = (
                    record.get("s3", {})
                    .get("object", {})
                    .get("key", {})
                    .rsplit("/", 2)[1]
                    .rsplit("_", 2)[0]
                )
                channel = (
                    record.get("s3", {})
                    .get("object", {})
                    .get("key", {})
                    .rsplit("/", 2)[1]
                    .rsplit("_", 2)[1]
                )
                agent_recording_key = s3_client.list_objects_v2(
                    Bucket=recording_bucket, Prefix=f"{mono_recording_prefix}{call_id}_AGENT"
                )
                customer_recording_key = s3_client.list_objects_v2(
                    Bucket=recording_bucket, Prefix=f"{mono_recording_prefix}{call_id}_CALLER"
                )

                # Check if both recordings exist, and skip processing if missing
                if (
                    customer_recording_key.get("KeyCount") == 0
                    or agent_recording_key.get("KeyCount") == 0
                ):
                    message = "Skipping merge operation since both files are not available yet."
                    logger.info(message)
                    continue

                # Download recordings
                customer_recording = s3_client.get_object(
                    Bucket=recording_bucket,
                    Key=customer_recording_key.get("Contents")[0].get("Key"),
                )
                agent_recording = s3_client.get_object(
                    Bucket=recording_bucket, Key=agent_recording_key.get("Contents")[0].get("Key")
                )

                # Set up output paths
                output_key = recording_file_prefix + call_id + ".wav"

                # Extract audio segments
                customer_segment = AudioSegment(
                    customer_recording["Body"].read(), sample_width=2, frame_rate=8000, channels=1
                )
                agent_segment = AudioSegment(
                    agent_recording["Body"].read(), sample_width=2, frame_rate=8000, channels=1
                )

                # If lengths don't match, then account for silence
                l_channel, r_channel = (
                    (customer_segment, agent_segment)
                    if customer_segment.duration_seconds > agent_segment.duration_seconds
                    else (agent_segment, customer_segment)
                )
                silent_segment = AudioSegment.silent(
                    (l_channel.frame_count() - r_channel.frame_count()) / 8, frame_rate=8000
                )
                r_channel_padded = silent_segment.append(r_channel, crossfade=0)

                # Create stereo segment
                stereo_sound = AudioSegment.from_mono_audiosegments(l_channel, r_channel_padded)
                with NamedTemporaryFile() as output_handle:
                    stereo_sound.export(output_handle.name, format="wav")
                    # Upload stereo audio to output bucket
                    s3_client.upload_file(
                        output_handle.name,
                        output_bucket,
                        output_key,
                        ExtraArgs={"ContentType": "audio/wav"},
                    )
                logger.info(
                    "Successfully saved merged audio to the S3 bucket %s for Call Id %s",
                    output_bucket,
                    call_id,
                )

                # Update event source table with channel recording
                update_event_source(call_id, channel, output_key)

        return "Successfully completed mono to stereo processing"
    except Exception as error:
        logger.error("Exception occurred: ")
        logger.error(error)
        raise error