/*
 * Code generated by Speakeasy (https://speakeasy.com). DO NOT EDIT.
 */

import * as z from "zod/v3";
import { safeParse } from "../lib/schemas.js";
import { ClosedEnum } from "../types/enums.js";
import { Result as SafeParseResult } from "../types/fp.js";
import * as types from "../types/primitives.js";
import { SDKValidationError } from "./sdkvalidationerror.js";

export type GetInvoiceRequest = {
  integrationConfigurationId: string;
  invoiceId: string;
};

/**
 * Invoice state.
 */
export const GetInvoiceState = {
  Draft: "draft",
  Invoiced: "invoiced",
  Notpaid: "notpaid",
  Overdue: "overdue",
  Paid: "paid",
  Pending: "pending",
  RefundRequested: "refund_requested",
  Refunded: "refunded",
  Scheduled: "scheduled",
} as const;
/**
 * Invoice state.
 */
export type GetInvoiceState = ClosedEnum<typeof GetInvoiceState>;

/**
 * Subscription period for this billing cycle. ISO 8601 timestamps.
 */
export type GetInvoicePeriod = {
  start: string;
  end: string;
};

/**
 * Invoice items.
 */
export type GetInvoiceItems = {
  /**
   * Partner's billing plan ID.
   */
  billingPlanId: string;
  /**
   * Partner's resource ID. If not specified, indicates installation-wide item.
   */
  resourceId?: string | undefined;
  /**
   * Start and end are only needed if different from the period's start/end. ISO 8601 timestamp.
   */
  start?: string | undefined;
  /**
   * Start and end are only needed if different from the period's start/end. ISO 8601 timestamp.
   */
  end?: string | undefined;
  /**
   * Invoice item name.
   */
  name: string;
  /**
   * Additional item details.
   */
  details?: string | undefined;
  /**
   * Item price. A dollar-based decimal string.
   */
  price: string;
  /**
   * Item quantity.
   */
  quantity: number;
  /**
   * Units for item's quantity.
   */
  units: string;
  /**
   * Item total. A dollar-based decimal string.
   */
  total: string;
};

/**
 * Invoice discounts.
 */
export type GetInvoiceDiscounts = {
  /**
   * Partner's billing plan ID.
   */
  billingPlanId: string;
  /**
   * Partner's resource ID. If not specified, indicates installation-wide discount.
   */
  resourceId?: string | undefined;
  /**
   * Start and end are only needed if different from the period's start/end. ISO 8601 timestamp.
   */
  start?: string | undefined;
  /**
   * Start and end are only needed if different from the period's start/end. ISO 8601 timestamp.
   */
  end?: string | undefined;
  /**
   * Discount name.
   */
  name: string;
  /**
   * Additional discount details.
   */
  details?: string | undefined;
  /**
   * Discount amount. A dollar-based decimal string.
   */
  amount: string;
};

export type GetInvoiceResponseBody = {
  /**
   * Whether the invoice is in the testmode (no real transaction created).
   */
  test?: boolean | undefined;
  /**
   * Vercel Marketplace Invoice ID.
   */
  invoiceId: string;
  /**
   * Partner-supplied Invoice ID, if applicable.
   */
  externalId?: string | undefined;
  /**
   * Invoice state.
   */
  state: GetInvoiceState;
  /**
   * User-readable invoice number.
   */
  invoiceNumber?: string | undefined;
  /**
   * Invoice date. ISO 8601 timestamp.
   */
  invoiceDate: string;
  /**
   * Subscription period for this billing cycle. ISO 8601 timestamps.
   */
  period: GetInvoicePeriod;
  /**
   * Moment the invoice was paid. ISO 8601 timestamp.
   */
  paidAt?: string | undefined;
  /**
   * Most recent moment the invoice was refunded. ISO 8601 timestamp.
   */
  refundedAt?: string | undefined;
  /**
   * Additional memo for the invoice.
   */
  memo?: string | undefined;
  /**
   * Invoice items.
   */
  items: Array<GetInvoiceItems>;
  /**
   * Invoice discounts.
   */
  discounts?: Array<GetInvoiceDiscounts> | undefined;
  /**
   * Invoice total amount. A dollar-based decimal string.
   */
  total: string;
  /**
   * The reason for refund. Only applicable for states "refunded" or "refund_request".
   */
  refundReason?: string | undefined;
  /**
   * Refund amount. Only applicable for states "refunded" or "refund_request". A dollar-based decimal string.
   */
  refundTotal?: string | undefined;
  /**
   * System creation date. ISO 8601 timestamp.
   */
  created: string;
  /**
   * System update date. ISO 8601 timestamp.
   */
  updated: string;
};

/** @internal */
export type GetInvoiceRequest$Outbound = {
  integrationConfigurationId: string;
  invoiceId: string;
};

/** @internal */
export const GetInvoiceRequest$outboundSchema: z.ZodType<
  GetInvoiceRequest$Outbound,
  z.ZodTypeDef,
  GetInvoiceRequest
> = z.object({
  integrationConfigurationId: z.string(),
  invoiceId: z.string(),
});

export function getInvoiceRequestToJSON(
  getInvoiceRequest: GetInvoiceRequest,
): string {
  return JSON.stringify(
    GetInvoiceRequest$outboundSchema.parse(getInvoiceRequest),
  );
}

/** @internal */
export const GetInvoiceState$inboundSchema: z.ZodNativeEnum<
  typeof GetInvoiceState
> = z.nativeEnum(GetInvoiceState);

/** @internal */
export const GetInvoicePeriod$inboundSchema: z.ZodType<
  GetInvoicePeriod,
  z.ZodTypeDef,
  unknown
> = z.object({
  start: types.string(),
  end: types.string(),
});

export function getInvoicePeriodFromJSON(
  jsonString: string,
): SafeParseResult<GetInvoicePeriod, SDKValidationError> {
  return safeParse(
    jsonString,
    (x) => GetInvoicePeriod$inboundSchema.parse(JSON.parse(x)),
    `Failed to parse 'GetInvoicePeriod' from JSON`,
  );
}

/** @internal */
export const GetInvoiceItems$inboundSchema: z.ZodType<
  GetInvoiceItems,
  z.ZodTypeDef,
  unknown
> = z.object({
  billingPlanId: types.string(),
  resourceId: types.optional(types.string()),
  start: types.optional(types.string()),
  end: types.optional(types.string()),
  name: types.string(),
  details: types.optional(types.string()),
  price: types.string(),
  quantity: types.number(),
  units: types.string(),
  total: types.string(),
});

export function getInvoiceItemsFromJSON(
  jsonString: string,
): SafeParseResult<GetInvoiceItems, SDKValidationError> {
  return safeParse(
    jsonString,
    (x) => GetInvoiceItems$inboundSchema.parse(JSON.parse(x)),
    `Failed to parse 'GetInvoiceItems' from JSON`,
  );
}

/** @internal */
export const GetInvoiceDiscounts$inboundSchema: z.ZodType<
  GetInvoiceDiscounts,
  z.ZodTypeDef,
  unknown
> = z.object({
  billingPlanId: types.string(),
  resourceId: types.optional(types.string()),
  start: types.optional(types.string()),
  end: types.optional(types.string()),
  name: types.string(),
  details: types.optional(types.string()),
  amount: types.string(),
});

export function getInvoiceDiscountsFromJSON(
  jsonString: string,
): SafeParseResult<GetInvoiceDiscounts, SDKValidationError> {
  return safeParse(
    jsonString,
    (x) => GetInvoiceDiscounts$inboundSchema.parse(JSON.parse(x)),
    `Failed to parse 'GetInvoiceDiscounts' from JSON`,
  );
}

/** @internal */
export const GetInvoiceResponseBody$inboundSchema: z.ZodType<
  GetInvoiceResponseBody,
  z.ZodTypeDef,
  unknown
> = z.object({
  test: types.optional(types.boolean()),
  invoiceId: types.string(),
  externalId: types.optional(types.string()),
  state: GetInvoiceState$inboundSchema,
  invoiceNumber: types.optional(types.string()),
  invoiceDate: types.string(),
  period: z.lazy(() => GetInvoicePeriod$inboundSchema),
  paidAt: types.optional(types.string()),
  refundedAt: types.optional(types.string()),
  memo: types.optional(types.string()),
  items: z.array(z.lazy(() => GetInvoiceItems$inboundSchema)),
  discounts: types.optional(
    z.array(z.lazy(() => GetInvoiceDiscounts$inboundSchema)),
  ),
  total: types.string(),
  refundReason: types.optional(types.string()),
  refundTotal: types.optional(types.string()),
  created: types.string(),
  updated: types.string(),
});

export function getInvoiceResponseBodyFromJSON(
  jsonString: string,
): SafeParseResult<GetInvoiceResponseBody, SDKValidationError> {
  return safeParse(
    jsonString,
    (x) => GetInvoiceResponseBody$inboundSchema.parse(JSON.parse(x)),
    `Failed to parse 'GetInvoiceResponseBody' from JSON`,
  );
}
