import { Activity, ActivityLike, ConversationReference, DeprecatedInputActivity, InvokeResponse, SentActivity, TokenStatus } from '@microsoft/teams.api';
import { Client as HttpClient, ILogger, IStorage } from '@microsoft/teams.common';
import { ApiClient, GraphClient } from '../api';
import { BotApiCredential, GraphCredential } from '../files/download';
import { IFilesAccessor } from '../files/types';
import { OAuthSignInOptions } from '../oauth';
import { Plan } from '../plan';
import { TurnStateContainer } from '../state';
import { IStreamer } from '../types';
import { IActivitySender } from '../types/plugin/sender';
/**
 * Constructor arguments for ActivityContext
 * Internal implementation details not exposed in public interface
 */
export interface IActivityContextConstructorArgs {
    /**
     * Graph credential used by the file path, selected per actor and resolved at fetch time.
     *
     * Constructor-only, and deliberately absent from {@link IBaseActivityContextOptions}: it exists so `ctx.files` can reach bytes the pre-authorized download URL cannot, and a handler has no reason to hold it. Declaring it here keeps it off the public context type and out of the instance, rather than advertising a property that is always `undefined`.
     */
    filesCredential?: GraphCredential;
    /**
     * Bot API credential used by the file path to read inline images, resolved at fetch time.
     *
     * Constructor-only for the same reason as {@link filesCredential}.
     */
    filesBotApiCredential?: BotApiCredential;
    /**
     * activity sender for sending activities and creating streams
     */
    activitySender: IActivitySender;
    /**
     * call the next event/middleware handler
     */
    next: (context?: IActivityContext) => (void | InvokeResponse) | Promise<void | InvokeResponse>;
    /**
     * Validates that a connection used by a deprecated OAuth helper is registered
     * and was named when registered flows require it.
     * @internal
     */
    validateOAuthConnection?: (connectionName: string, connectionNameProvided: boolean) => void;
    /**
     * Records pending OAuth attribution after the deprecated `signin()` helper
     * sends a card for a registered connection.
     * @internal
     */
    onOAuthSignInInitiated?: (context: IActivityContext, connectionName: string, supportsSso: boolean) => void | Promise<void>;
    /**
     * Gets corrected connection status through the app's OAuth registry.
     * @internal
     */
    getOAuthConnectionStatus?: (context: IActivityContext) => Promise<TokenStatus[]>;
}
/**
 * Base activity context options
 * These are the public properties exposed on the context
 */
export interface IBaseActivityContextOptions<T extends Activity = Activity> {
    /**
     * the app id of the bot
     */
    appId: string;
    /**
     * the inbound activity
     */
    activity: T;
    /**
     * the inbound activity conversation reference
     */
    ref: ConversationReference;
    /**
     * the app logger instance
     */
    log: ILogger;
    /**
     * the api client
     */
    api: ApiClient;
    /**
     * the app's shared HTTP client, used for outbound calls that are not part of the Teams API surface
     * (e.g. downloading an inbound file's bytes)
     * They inherit the app's User-Agent, middleware, and configuration.
     */
    client?: HttpClient;
    /**
     * the app graph client
     */
    appGraph: GraphClient;
    /**
     * the user graph client
     *
     * @deprecated Use a registered OAuth flow to acquire the token needed by the
     * Microsoft Graph operation. This property remains available for compatibility.
     */
    userGraph: GraphClient;
    /**
     * app storage instance
     *
     * @deprecated Use `state` for conversation or user state. Applications that
     * need general persistence should own and use their storage provider directly.
     */
    storage: IStorage;
    /**
     * Conversation and user state loaded for this activity turn.
     *
     * This is undefined when state is disabled or the activity has no conversation ID.
     * Do not retain the container after the handler completes; its scopes are sealed.
     */
    state?: TurnStateContainer;
    /**
     * whether the user has provided
     * their MSGraph credentials for use
     * via `api.user.*`
     *
     * @deprecated Use `app.getOAuthFlow(connectionName).isSignedIn(ctx)`.
     */
    isSignedIn?: boolean;
    /**
     * the default connection name to use for the app
     * @default `graph`
     * @deprecated Register and retain the required `OAuthFlow` explicitly.
     */
    connectionName: string;
    /**
     * the user token for the activity context
     *
     * @deprecated Use `app.getOAuthFlow(connectionName).getToken(ctx)`.
     */
    userToken?: string;
}
export type IActivityContextOptions<T extends Activity = Activity, TExtraCtx extends Record<string, any> = Record<string, any>> = IBaseActivityContextOptions<T> & TExtraCtx;
export interface IBaseActivityContext<T extends Activity = Activity, TExtraCtx extends Record<string, any> = Record<string, any>> extends IBaseActivityContextOptions<T> {
    /**
     * a stream that can emit activity chunks
     *
     * The first message of the stream goes to the reply chain (thread) where `send` would place a response.
     * In a chat the stream starts in the thread when the inbound activity is in a thread, and at top level otherwise.
     * In a channel the stream starts in the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, the first message of the stream is created in the inbound conversation instead.
     * Without `channelData.replyChain.id` the stream is not placed in a reply chain.
     */
    stream: IStreamer;
    /**
     * the uploaded files on the current inbound activity, i.e. `contentType: file.download.info` subset of `activity.attachments`, plus images pasted inline, mapped to `IncomingFile`. See {@link IFilesAccessor}.
     */
    files: IFilesAccessor;
    /**
     * Get the Plan bound to this inbound activity. Use new Plan(options) for a saved prompt.
     * In a chat thread, a standalone `complete()` is posted to the reply chain, as `ctx.send` does.
     * Typing updates, completions in a channel, and prompts outside a thread use the conversation.
     *
     * @experimental This API is in preview and may change in the future.
     * Diagnostic: ExperimentalTeamsPlan
     */
    plan(): Plan;
    /**
     * call the next event/middleware handler
     */
    next: (context?: IActivityContext & TExtraCtx) => (void | InvokeResponse) | Promise<void | InvokeResponse>;
    /**
     * send an activity to the conversation
     * @param activity activity to send
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    send(activity: DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send an activity to the conversation
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     *
     * @param activity activity to send
     */
    send(activity: ActivityLike): Promise<SentActivity>;
    /**
     * send an activity to the conversation
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     *
     * @param activity activity to send
     */
    send(activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`
     * @param activity activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a `DeprecatedInputActivity` is deprecated. Use MessageActivityInput or TypingActivityInput instead.
     * Passing a conversation reference is also deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: DeprecatedInputActivity, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`
     * @param activity activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a conversation reference is deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: ActivityLike, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`
     * @param activity activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a conversation reference is deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: ActivityLike | DeprecatedInputActivity, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    reply(activity: DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * reply to the inbound activity, automatically quoting the inbound message
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * The response is automatically quoted only when the inbound activity id is a plain numeric message id.
     * Otherwise (for example an invoke or a card action with a service-generated `f:` id) the activity is sent without a quote, exactly like {@link send}.
     * Explicit quotes through {@link quote} are unchanged.
     *
     * @param activity activity to send
     */
    reply(activity: ActivityLike): Promise<SentActivity>;
    /**
     * reply to the inbound activity, automatically quoting the inbound message
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * The response is automatically quoted only when the inbound activity id is a plain numeric message id.
     * Otherwise (for example an invoke or a card action with a service-generated `f:` id) the activity is sent without a quote, exactly like {@link send}.
     * Explicit quotes through {@link quote} are unchanged.
     *
     * @param activity activity to send
     */
    reply(activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send a reply quoting a specific message by ID
     * @param messageId the ID of the message to quote
     * @param activity activity to send
     */
    /**
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    quote(messageId: string, activity: DeprecatedInputActivity): Promise<SentActivity>;
    quote(messageId: string, activity: ActivityLike): Promise<SentActivity>;
    quote(messageId: string, activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * trigger user signin flow for the activity sender
     * @param options options for the signin flow
     * @deprecated Register a connection with `app.addOAuthFlow(...)` and call
     * `flow.signIn(ctx, options)` instead.
     */
    signin: (options?: OAuthSignInOptions) => Promise<string | undefined>;
    /**
     * sign the activity sender out
     * @param name auth connection name, defaults to `graph`
     * @deprecated Register a connection with `app.addOAuthFlow(...)` and call
     * `flow.signOut(ctx)` instead.
     */
    signout: (name?: string) => Promise<void>;
    /**
     * Gets token status for every registered OAuth connection.
     *
     * Connections reported as disconnected after silent SSO are verified with a
     * direct token lookup. A connected flow omitted by the status endpoint is
     * returned with an empty `serviceProviderDisplayName` because that value is
     * unavailable from the token response.
     */
    getConnectionStatus: () => Promise<TokenStatus[]>;
}
export type IActivityContext<T extends Activity = Activity, TExtraContext = unknown> = IBaseActivityContext<T> & (TExtraContext extends Record<string, any> ? TExtraContext : {});
export declare class ActivityContext<T extends Activity = Activity, TExtraCtx extends {} = {}> implements IBaseActivityContext<T, TExtraCtx> {
    appId: string;
    activity: T;
    ref: ConversationReference;
    log: ILogger;
    api: ApiClient;
    appGraph: GraphClient;
    userGraph: GraphClient;
    /**
     * @deprecated Use `state` for conversation or user state.
     */
    storage: IStorage;
    state?: TurnStateContainer;
    stream: IStreamer;
    files: IFilesAccessor;
    isSignedIn?: boolean;
    connectionName: string;
    next: (context?: IActivityContext) => (void | InvokeResponse) | Promise<void | InvokeResponse>;
    [key: string]: any;
    private activitySender;
    private _plan?;
    private readonly validateOAuthConnection?;
    private readonly onOAuthSignInInitiated?;
    private readonly getOAuthConnectionStatus?;
    constructor(value: IBaseActivityContextOptions & IActivityContextConstructorArgs);
    /**
     * Get the Plan bound to this inbound activity, scoping its client on first access.
     * In a chat thread, a standalone `complete()` is posted to the reply chain, as `ctx.send` does.
     * Typing updates, completions in a channel, and prompts outside a thread use the conversation.
     *
     * @experimental This API is in preview and may change in the future.
     * Diagnostic: ExperimentalTeamsPlan
     */
    plan(): Plan;
    /**
     * send an activity in the current conversation without quoting.
     *
     * @param activity the activity to send
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    send(activity: DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send an activity in the current conversation without quoting.
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * To send with a visual quote of the inbound message, use {@link reply}.
     *
     * @param activity the activity to send
     */
    send(activity: ActivityLike): Promise<SentActivity>;
    /**
     * send an activity in the current conversation without quoting.
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * To send with a visual quote of the inbound message, use {@link reply}.
     *
     * @param activity the activity to send
     */
    send(activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`.
     *
     * @param activity the activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a `DeprecatedInputActivity` is deprecated. Use MessageActivityInput or TypingActivityInput instead.
     * Passing a conversation reference is also deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: DeprecatedInputActivity, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`.
     *
     * @param activity the activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a conversation reference is deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: ActivityLike, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * send an activity to the conversation referenced by `conversationRef`.
     *
     * @param activity the activity to send
     * @param conversationRef conversation reference to send to
     * @deprecated Passing a conversation reference is deprecated and will be removed in a future release. Use `App.send()` to send to a different conversation.
     * `App.send()` sends through the `serviceUrl` the app is configured with, unlike the context methods, which use the `serviceUrl` of the conversation reference (by default, the inbound activity's).
     */
    send(activity: ActivityLike | DeprecatedInputActivity, conversationRef?: ConversationReference): Promise<SentActivity>;
    /**
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    reply(activity: DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * send an activity in the current conversation with a visual quote
     * of the inbound message.
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * The response is automatically quoted only when the inbound activity id is a plain numeric message id.
     * Otherwise (for example an invoke or a card action with a service-generated `f:` id) the activity is sent without a quote, exactly like {@link send}.
     * Explicit quotes through {@link quote} are unchanged.
     * To send without quoting, use {@link send}.
     *
     * @param activity the activity to send
     */
    reply(activity: ActivityLike): Promise<SentActivity>;
    /**
     * send an activity in the current conversation with a visual quote
     * of the inbound message.
     *
     * In a chat, sends into the reply chain (thread) when the inbound activity is inside one, and at top level otherwise.
     * The inbound activity can be a message, a card action, an invoke, a reaction, an edit or a delete.
     * In a channel, sends into the reply chain of the inbound message.
     * In a channel, when the service answers HTTP 404, sends to the inbound conversation instead.
     * Inbound activities without `channelData.replyChain.id`, and other inbound activities, are not placed, and the activity is sent to the inbound conversation.
     * The response is automatically quoted only when the inbound activity id is a plain numeric message id.
     * Otherwise (for example an invoke or a card action with a service-generated `f:` id) the activity is sent without a quote, exactly like {@link send}.
     * Explicit quotes through {@link quote} are unchanged.
     * To send without quoting, use {@link send}.
     *
     * @param activity the activity to send
     */
    reply(activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    /**
     * Send a message to the conversation with a quoted message reference prepended to the text.
     * Teams renders the quoted message as a preview bubble above the response text.
     * @param messageId - The ID of the message to quote
     * @param activity - The activity to send — a quote placeholder for messageId will be prepended to its text
     */
    /**
     * @deprecated Use MessageActivityInput or TypingActivityInput instead.
     */
    quote(messageId: string, activity: DeprecatedInputActivity): Promise<SentActivity>;
    quote(messageId: string, activity: ActivityLike): Promise<SentActivity>;
    quote(messageId: string, activity: ActivityLike | DeprecatedInputActivity): Promise<SentActivity>;
    signin(options?: OAuthSignInOptions): Promise<string | undefined>;
    signout(connectionName?: string): Promise<void>;
    getConnectionStatus(): Promise<TokenStatus[]>;
    toInterface(): IActivityContext;
    private isIncomingTargeted;
    private shouldOutboundBeAutoTargeted;
    /**
     * Finds the chat or channel and reply chain (thread) a response to the inbound activity is posted to.
     *
     * In a channel a response to a message always goes to the reply chain of the inbound message: `channelData.replyChain.id` is the root message of the thread, and it equals the inbound message's own id for a top-level post.
     * The destination is the channel, `channelData.channel.id`.
     * Other inbound activities in a channel are not placed.
     *
     * In a chat see `isInsideThread` for which activities are inside a thread.
     * The destination is the chat, `channelData.chat.id`.
     * When the inbound activity is on a top-level message the response is sent as a top-level message.
     *
     * Placement depends only on the payload: without `channelData.replyChain.id` and the chat or channel id the activity is not placed.
     * Returns undefined when an id is missing or blank, so the send goes to the inbound conversation.
     */
    private getInboundReplyChainPlacement;
    /**
     * Whether the inbound activity in a chat is inside a thread: `channelData.replyChain.id` differs from the id of the message the activity acts on.
     * The message it acts on is:
     * - `activity.id` for a message, an edit and a delete.
     * - `replyToId` (the reacted message) for a reaction and for a message sent by a card button (a message with `channelData.source`).
     * - `value.messagePayload.id` for a message action, and `replyToId` (the message the user acted on, for example a card or a message with feedback buttons) for any other invoke.
     *
     * An invoke that is not tied to a message (for example a compose-box extension or a `task/fetch` from a bot command) is inside a thread when `channelData.replyChain.id` is present.
     * A `replyToId` or `messagePayload.id` that is not a plain number is never inside a thread, and neither are other inbound activities.
     * A `source` without a non-empty string `name` and a `replyToId` that is null count as absent.
     */
    private isInsideThread;
    private getChatReplyChainPlacement;
    private isSameConversation;
    private applyTargetedRecipient;
    private isTargetedOutbound;
    private stripQuotedReplyMetadata;
    private addTargetedMessageInfo;
}
