> For the complete documentation index, see [llms.txt](https://docs.nubrick.app/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.nubrick.app/reference/android/nubricksdk.md).

# NubrickSDK

`NubrickSDK` は Android SDK のエントリポイントです。Kotlin/Jetpack Compose と Java/XML のどちらからも、初期化、イベント送信、埋め込み、Remote Config、ユーザープロパティ更新を扱えます。

{% hint style="warning" %}
`NubrickSDK.initialize(...)` は、アプリ起動時に 1 回だけ実行してください。\
推奨: `Application` の `onCreate` で初期化してください。\
`Embedding` / `RemoteConfig` / `dispatch` などの API は、初期化完了後に利用してください。\
Compose でオーバーレイ配信を表示する場合は `NubrickProvider { ... }` でルートを包み、XML では `NubrickOverlayView` をアプリのコンテンツより上に配置してください。
{% endhint %}

### 定義 <a href="#definition" id="definition"></a>

```kotlin
object NubrickSDK {
    fun initialize(
        context: Context,
        config: Config
    )

    fun createConfig(
        projectId: String,
        onEventListener: NubrickGlobalEventListener? = null,
        onDispatchListener: NubrickDispatchListener? = null,
        trackCrashes: Boolean = true
    ): Config

    fun dispatch(event: NubrickEvent)

    fun setUserId(id: String)
    fun getUserId(): String?

    fun setUserProperty(key: String, value: Any)
    fun getUserProperty(key: String): String?

    fun setUserProperties(props: Map<String, Any>)
    fun getUserProperties(): Map<String, String>

    @Composable
    fun Embedding(
        id: String,
        modifier: Modifier = Modifier,
        arguments: Any? = null,
        onEvent: ((event: Event) -> Unit)? = null,
        content: (@Composable (state: EmbeddingLoadingState) -> Unit)? = null,
        onSizeChange: ((width: NubrickSize, height: NubrickSize) -> Unit)? = null
    )

    @Composable
    fun RemoteConfig(
        id: String,
        content: @Composable (RemoteConfigLoadingState) -> Unit
    )

    fun remoteConfig(id: String): Result<app.nubrick.nubrick.remoteconfig.RemoteConfig>

    fun fetchRemoteConfig(
        id: String,
        listener: RemoteConfigListener
    )
}

data class Config(
    val projectId: String,
    val onEvent: ((event: Event) -> Unit)? = null,
    val onDispatch: ((event: NubrickEvent) -> Unit)? = null,
    val trackCrashes: Boolean = true,
)

sealed class NubrickSize {
    data class Fixed(val value: Int) : NubrickSize()
    data object Fill : NubrickSize()
}

fun interface NubrickSizeListener {
    fun onSizeChange(width: NubrickSize, height: NubrickSize)
}
```

### 初期化 <a href="#init" id="init"></a>

#### Kotlin / Compose

```kotlin
import android.app.Application
import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import app.nubrick.nubrick.Config
import app.nubrick.nubrick.NubrickProvider
import app.nubrick.nubrick.NubrickSDK

class MyApp : Application() {
    override fun onCreate() {
        super.onCreate()
        NubrickSDK.initialize(
            context = this,
            config = Config(projectId = "<YOUR_PROJECT_ID>")
        )
    }
}

class MainActivity : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        setContent {
            NubrickProvider {
                AppContent()
            }
        }
    }
}
```

#### Java / XML

`Application` の `onCreate` で `Config` を作成し、SDK を初期化します。

```java
import android.app.Application;

import app.nubrick.nubrick.Config;
import app.nubrick.nubrick.NubrickSDK;

public final class MyApp extends Application {
    @Override
    public void onCreate() {
        super.onCreate();

        Config config = new Config("<YOUR_PROJECT_ID>");
        NubrickSDK.initialize(this, config);
    }
}
```

アプリ全体のイベントを受け取る場合は、`NubrickGlobalEventListener` と `NubrickDispatchListener` を設定できる `createConfig(...)` を利用します。

```java
Config config = NubrickSDK.createConfig(
    "<YOUR_PROJECT_ID>",
    event -> System.out.println("Event: " + event.getName()),
    event -> System.out.println("Dispatched: " + event.getName()),
    true
);
NubrickSDK.initialize(this, config);
```

`trackCrashes` だけを変更する場合は、`NubrickSDK.createConfig("<YOUR_PROJECT_ID>", false)` を利用できます。

### イベント送信 <a href="#events" id="events"></a>

カスタムイベントを発火させる

{% tabs %}
{% tab title="Kotlin" %}

```kotlin
import app.nubrick.nubrick.NubrickEvent
import app.nubrick.nubrick.NubrickSDK

NubrickSDK.dispatch(NubrickEvent("PURCHASE_COMPLETED"))
```

{% endtab %}

{% tab title="Java" %}

```java
import app.nubrick.nubrick.NubrickEvent;
import app.nubrick.nubrick.NubrickSDK;

NubrickSDK.dispatch(new NubrickEvent("PURCHASE_COMPLETED"));
```

{% endtab %}
{% endtabs %}

### 埋め込み（Compose） <a href="#compose" id="compose"></a>

```kotlin
NubrickSDK.Embedding("TOP_COMPONENT")
```

フェーズを使う場合：

```kotlin
import app.nubrick.nubrick.component.EmbeddingLoadingState

NubrickSDK.Embedding("TOP_COMPONENT") { state ->
    when (state) {
        is EmbeddingLoadingState.Loading -> CircularProgressIndicator()
        is EmbeddingLoadingState.Completed -> state.view()
        is EmbeddingLoadingState.NotFound -> Text("not found")
        is EmbeddingLoadingState.Failed -> Text("error")
    }
}
```

### 埋め込み（Java / XML） <a href="#xml" id="xml"></a>

XML に `NubrickEmbeddingView` を追加し、`nubrickExperimentId` にエクスペリメントIDまたはIDエイリアスを指定します。

```xml
<app.nubrick.nubrick.view.NubrickEmbeddingView
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/nubrick_embedding"
    android:layout_width="match_parent"
    android:layout_height="240dp"
    app:nubrickExperimentId="TOP_COMPONENT" />
```

エクスペリメントIDは Java から変更することもできます。

```java
import app.nubrick.nubrick.view.NubrickEmbeddingView;

NubrickEmbeddingView embeddingView = findViewById(R.id.nubrick_embedding);
embeddingView.setExperimentId("TOP_COMPONENT");
```

イベントと引数を設定する場合：

```java
import app.nubrick.nubrick.view.NubrickEmbeddingView;

import java.util.Collections;

NubrickEmbeddingView embeddingView = findViewById(R.id.nubrick_embedding);
embeddingView.setArguments(
    Collections.singletonMap("item_id", itemId)
);
embeddingView.setOnEventListener(event -> {
    System.out.println("Event: " + event.getName());
});
```

読み込み状態ごとのビューをカスタマイズする場合は、アプリモジュールで Kotlin/Jetpack Compose を有効にし、埋め込み部分だけを `NubrickSDK.Embedding(...)` で実装して、`ComposeView` を介して既存の XML レイアウトに組み込んでください。

### 埋め込みサイズ <a href="#size" id="size"></a>

#### Kotlin / Compose

`onSizeChange` を使うと、埋め込みコンポーネントの実サイズを取得できます。\
このコールバックは、実際の埋め込みページが読み込まれたときだけ呼ばれます。`Loading` / `NotFound` / `Failed` では呼ばれません。

```kotlin
NubrickSDK.Embedding(
    id = "TOP_COMPONENT",
    onSizeChange = { width, height ->
        println("width=$width, height=$height")
    }
)
```

`NubrickSize` の意味:

* `NubrickSize.Fixed(value)` は、エディタで固定サイズが設定されていることを表します。
* `NubrickSize.Fill` は、その軸に固定サイズがなく、ホスト側のレイアウトに従うことを表します。

#### Java / XML

`NubrickEmbeddingView` に `wrap_content` を指定した軸には、エディタ側の固定サイズが自動的に反映されます。エディタ側が `fill` の場合は、親ビューの制約に従います。

```xml
<app.nubrick.nubrick.view.NubrickEmbeddingView
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    app:nubrickExperimentId="TOP_COMPONENT" />
```

`setOnSizeChangeListener(...)` を使うと、埋め込みコンポーネントの実サイズを受け取れます。このリスナーは、実際の埋め込みページが読み込まれたときだけ呼び出されます。`NubrickSize.Fixed` の値は `getValue()` で取得できます。

```java
import app.nubrick.nubrick.NubrickSize;
import app.nubrick.nubrick.view.NubrickEmbeddingView;

NubrickEmbeddingView embeddingView = findViewById(R.id.nubrick_embedding);
embeddingView.setOnSizeChangeListener((width, height) -> {
    if (width instanceof NubrickSize.Fixed) {
        int fixedWidth = ((NubrickSize.Fixed) width).getValue();
        System.out.println("width=" + fixedWidth);
    }
});
```

### Remote Config

#### Kotlin / Compose

```kotlin
import app.nubrick.nubrick.remoteconfig.RemoteConfigLoadingState

NubrickSDK.RemoteConfig("FEATURE_FLAGS") { state ->
    when (state) {
        is RemoteConfigLoadingState.Completed -> {
            val enabled = state.variant.getAsBoolean("new_checkout") ?: false
            Text("enabled=$enabled")
        }
        is RemoteConfigLoadingState.Loading -> CircularProgressIndicator()
        is RemoteConfigLoadingState.NotFound -> Text("not found")
        is RemoteConfigLoadingState.Failed -> Text("error")
    }
}
```

#### Java

Java では `fetchRemoteConfig(...)` で非同期に取得し、`RemoteConfigListener` で結果を受け取ります。このコールバックはメインスレッド上で呼び出されます。

```java
import app.nubrick.nubrick.remoteconfig.RemoteConfigVariant;

NubrickSDK.fetchRemoteConfig("FEATURE_FLAGS", result -> {
    if (!result.isSuccess()) {
        System.err.println(result.getError());
        return;
    }

    RemoteConfigVariant variant = result.getValue();
    if (variant == null) {
        return;
    }

    Boolean enabled = variant.getAsBoolean("new_checkout");
    System.out.println("enabled=" + enabled);
});
```

### ユーザープロパティ <a href="#properties" id="properties"></a>

{% hint style="warning" %}
この値は、エクスペリメントのデータを識別するためにNubrickサーバーに送信されます。そのため、氏名やメールアドレスなどの個人情報は、user\_id として使用しないでください。\
詳細はこちらのドキュメントもご覧ください。

[ユーザー属性情報（setProperties）について](/other/setproperties.md)
{% endhint %}

{% hint style="info" %}
このプロパティは、

* どのユーザーがエクスペリメントのターゲットとなるかをフィルタリングする
* エクスペリメント内のユーザー毎の動的な変数として表示する

ために使用されます。
{% endhint %}

#### Kotlin

```kotlin
NubrickSDK.setUserProperties(
    mapOf(
        "plan" to "gold",
        "isPremium" to true,
        "age" to 32
    )
)

NubrickSDK.setUserId("<CUSTOM_USER_ID>")

val userId = NubrickSDK.getUserId()
val props = NubrickSDK.getUserProperties()
```

#### Java

```java
import java.util.HashMap;
import java.util.Map;

Map<String, Object> properties = new HashMap<>();
properties.put("plan", "gold");
properties.put("isPremium", true);
properties.put("age", 32);
NubrickSDK.setUserProperties(properties);

NubrickSDK.setUserProperty("prefecture", "Tokyo");
String prefecture = NubrickSDK.getUserProperty("prefecture");

NubrickSDK.setUserId("<CUSTOM_USER_ID>");

String userId = NubrickSDK.getUserId();
Map<String, String> props = NubrickSDK.getUserProperties();
```

### ビルトインのユーザープロパティ <a href="#builtin" id="builtin"></a>

デフォルトで、以下のビルトインプロパティが設定されています：

| Key            | Description                                           |
| -------------- | ----------------------------------------------------- |
| `userId`       | User id (uuid by default)                             |
| `languageCode` | language code (e.g. ja for Japanese, en for English)  |
| `regionCode`   | region code (e.g. JP for Japan, US for United States) |
| `sdkVersion`   | nubrick sdk version                                   |
| `osName`       | os name (Android)                                     |
| `osVersion`    | Android API level                                     |
| `appId`        | your app package name                                 |
| `appVersion`   | your app version                                      |

### 補足 <a href="#notes" id="notes"></a>

* `setUserProperties` / `setUserProperty` の値は `String`, `Boolean`, `Int`, `Double` などを渡せます。
* プロパティのキーは半角英数字と `_` `-` のみ利用できます。camelCase（`isPremium` など）を推奨します。詳細は [ユーザー属性情報（setProperties）について](/other/setproperties.md) を参照してください。
* `getUserProperties()` は、アプリが設定したカスタム値と `userId` を取得できます。
* 失敗系の状態は [Phases](/reference/android/phases.md) を参照してください。


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://docs.nubrick.app/reference/android/nubricksdk.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
