NPC Connection error on iOS

Hi developers,

This is a factual timeline of exactly what has happened since the last successful build (#132) after we upgraded to Convai SDK 4.1.0.

Build #132 (last good run):
Everything worked on iPhone — NPC voice connection, microphone permission, and audio session were all functioning correctly.
The three files that were in the project at that time are attached below exactly as they existed for #132 (we have since restored them multiple times).

What happened next (builds #133 through #138):

  • We made no intentional code changes between #132 and #133.

  • Build #133 and every build after it showed the same “connection error” on the iPhone immediately when selecting an NPC.

  • The iPhone logs no longer contained any of the debug lines from ConvaiAudioSessionManager or the native stub (“Permission GRANTED”, “AVAudioSession fully configured”, etc.).

  • We tried re-committing the exact same three files that worked in #132 (link.xml, ConvaiAudioSessionManager.cs, ConvaiAudioStub.mm) multiple times.

  • Build #138 failed to compile with this error: Assets/Scripts/NPCSelectionScreenManager.cs(120,13): error CS0117: ‘ConvaiAudioSessionManager’ does not contain a definition for ‘Configure’ (and the same error for HasPermission calls).

To fix the compile error I restored the missing static Configure() and HasPermission() methods while keeping the early-init logic we had been testing. I have not changed anything else.

Current files in the project (the ones that will be in build #139):

1. link.xml (unchanged since #132)

XML

<linker>
  <assembly fullname="Assembly-CSharp" preserve="all"/>
  <assembly fullname="Assembly-CSharp-firstpass" preserve="all"/>
</linker>

2. ConvaiAudioSessionManager.cs (full file — this is the version that fixes the compile error)

C#

using UnityEngine;
using System.Runtime.InteropServices;
using System.Collections;

public class ConvaiAudioSessionManager : MonoBehaviour
{
    [DllImport("__Internal")]
    private static extern void __RequestAudioSessionAndConfigure();

    [DllImport("__Internal")]
    private static extern bool __IsMicPermissionGranted();

    [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)]
    private static void InitializeVeryEarly()
    {
        Debug.Log("=== EARLY AUDIO INIT BUILD 139 - Running BEFORE any scene loads ===");
        if (Application.platform == RuntimePlatform.IPhonePlayer)
        {
            __RequestAudioSessionAndConfigure();
        }
    }

    private void Awake()
    {
        DontDestroyOnLoad(gameObject);
        Debug.Log("=== ConvaiAudioSessionManager Awake called ===");
    }

    private IEnumerator Start()
    {
        yield return null;

        Debug.Log("[ConvaiAudioSessionManager] Requesting microphone permission...");
        if (!Application.HasUserAuthorization(UserAuthorization.Microphone))
        {
            yield return Application.RequestUserAuthorization(UserAuthorization.Microphone);
        }

        if (Application.HasUserAuthorization(UserAuthorization.Microphone))
        {
            Debug.Log("[ConvaiAudioSessionManager] Permission GRANTED");
            __RequestAudioSessionAndConfigure();
        }
        else
        {
            Debug.LogError("[ConvaiAudioSessionManager] Microphone permission DENIED");
        }
    }

    public static void Configure()
    {
        Debug.Log("[ConvaiAudioSessionManager] Configure() called from other script");
        if (Application.platform == RuntimePlatform.IPhonePlayer)
        {
            __RequestAudioSessionAndConfigure();
        }
    }

    public static bool HasPermission() => Application.HasUserAuthorization(UserAuthorization.Microphone);
}

3. ConvaiAudioStub.mm (unchanged since #132)

Objective-C

#import <AVFoundation/AVFoundation.h>
#import <Foundation/Foundation.h>

extern "C" {
void ConfigureLiveKitAudioSession() {
AVAudioSession *session = [AVAudioSession sharedInstance];
NSError *error = nil;

[session setCategory:AVAudioSessionCategoryPlayAndRecord
withOptions:AVAudioSessionCategoryOptionDefaultToSpeaker |
AVAudioSessionCategoryOptionAllowBluetooth |
AVAudioSessionCategoryOptionMixWithOthers
error:&error];

if (error) NSLog(@"[ConvaiAudioStub] setCategory error: %@", error);

[session setMode:AVAudioSessionModeVoiceChat error:&error];
if (error) NSLog(@"[ConvaiAudioStub] setMode error: %@", error);

[session setActive:YES
withOptions:AVAudioSessionSetActiveOptionNotifyOthersOnDeactivation
error:&error];

if (error) {
NSLog(@"[ConvaiAudioStub] setActive error: %@", error);
} else {
NSLog(@"[ConvaiAudioStub] ✅ AVAudioSession fully configured for LiveKit voice");
}
}

__attribute__((visibility("default")))
bool __IsMicPermissionGranted() {
NSLog(@"[ConvaiAudioStub] __IsMicPermissionGranted called → returning YES");
return true;
}

__attribute__((visibility("default")))
void __RequestAudioSessionAndConfigure() {
NSLog(@"[ConvaiAudioStub] __RequestAudioSessionAndConfigure called → configuring LiveKit");
ConfigureLiveKitAudioSession();
}

// Legacy catch-alls
__attribute__((visibility("default"))) void Configure() { ConfigureLiveKitAudioSession(); }
__attribute__((visibility("default"))) void _Configure() { ConfigureLiveKitAudioSession(); }
__attribute__((visibility("default"))) void __Configure() { ConfigureLiveKitAudioSession(); }
__attribute__((visibility("default"))) void RequestAudioSessionAndConfigure() { ConfigureLiveKitAudioSession(); }
__attribute__((visibility("default"))) void _RequestAudioSessionAndConfigure() { ConfigureLiveKitAudioSession(); }
}

I am now running build #139 with exactly these files. I will send you the new iPhone log as soon as it finishes.

That is everything that has happened since #132. No other changes were made to the project.

here is compact build log from run #139

build 139.txt (207.4 KB)

anyone can help

I have informed my teammates, and they will check it during working hours.

I would also like to point out that this is a beta package, so unexpected issues may occur. On our side, iOS testing has been running without any problems. My assumption is that some of the custom changes in your project may be causing the issue.

Additionally, there is currently a known issue when switching from one Convai scene to another Convai scene.

My suggestion is this: please create a new project, import Convai 4.1.0, add your API key, and build the Convai Basic Sample from the Convai Samples for iOS. If it works without any issues, then the problem is likely not with the iOS build itself.

Could you please verify this and let me know?

I will give it a try

ok I tried and am getting these errors

2475800724050-godsvoice-godsvoices-29.log (4.5 MB)

You aren’t using a new project, and you’re using our v3 plugin. Please create a new project, import Convai 4.1.0, add your API key, and build the Convai Basic Sample from the Convai Samples for iOS. If it works without any issues, then the problem is likely not with the iOS build itself.