> ## Documentation Index
> Fetch the complete documentation index at: https://docs.base44.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Start scheduling posts

> <Info>This API is in beta. Endpoints, fields, and behavior may still change, so avoid depending on it in production.</Info>

Hands the app's approved posts to the publisher, so each one goes out at its own scheduled time.

The work runs in the background. This endpoint answers 202 with a `job_id`; poll [Get scheduling job](/api-reference/get-scheduling-job) to see how it went. A second start for the same app fails with a 409 while the first one is still starting.

Calling it again for the same window normally returns the job already in flight instead of starting a second one, but treat that as best-effort rather than a guarantee: a retry sent in the moment before the job starts running can come back with a new `job_id`. Nothing is published twice when that happens, because both runs resolve the same automation for a given post.

It takes the posts whose `scheduled_at` falls in `[scheduled_from, scheduled_until)` and that aren't handed over yet, which means the posts you approved plus the ones an earlier run couldn't place. A post still in `proposal` isn't taken at all, so approve it first. A range holding more than 100 such posts fails with a 422; schedule it in smaller ranges.

Placing a post can fail for reasons this endpoint can't check up front, and each one is counted in the job's `result` rather than failing the request:

- The workspace is on the free plan. Publishing scheduled posts needs a paid workspace plan, and those posts are counted in `plan_limited`.
- The app has no connected account for the post's platform with publishing permission, or it has more than one. Those posts move to `needs_reconnect` and are counted there, and a later run picks them up once you fix the connection.
- The post's platform can't be published to at all, or its scheduled time has already passed. Those posts move to `failed`, which is final.

The social calendar endpoints share two rate limits: 20 requests per minute across creating, editing, deleting and approving posts, and 40 requests per minute across the rest. This endpoint counts against the 40.

<Note>This endpoint accepts a personal API key. Workspace API keys are not authorized for it and are rejected with a 403.</Note>



## OpenAPI

````yaml /developers/references/app-management/app-management-openapi.json post /api/apps/{app_id}/social-calendar/posts/schedule
openapi: 3.1.0
info:
  title: Base44 App Management API
  version: 1.0.0
servers:
  - url: https://app.base44.com
security:
  - ApiKeyAuth: []
paths:
  /api/apps/{app_id}/social-calendar/posts/schedule:
    post:
      summary: Start scheduling posts
      description: >-
        <Info>This API is in beta. Endpoints, fields, and behavior may still
        change, so avoid depending on it in production.</Info>


        Hands the app's approved posts to the publisher, so each one goes out at
        its own scheduled time.


        The work runs in the background. This endpoint answers 202 with a
        `job_id`; poll [Get scheduling job](/api-reference/get-scheduling-job)
        to see how it went. A second start for the same app fails with a 409
        while the first one is still starting.


        Calling it again for the same window normally returns the job already in
        flight instead of starting a second one, but treat that as best-effort
        rather than a guarantee: a retry sent in the moment before the job
        starts running can come back with a new `job_id`. Nothing is published
        twice when that happens, because both runs resolve the same automation
        for a given post.


        It takes the posts whose `scheduled_at` falls in `[scheduled_from,
        scheduled_until)` and that aren't handed over yet, which means the posts
        you approved plus the ones an earlier run couldn't place. A post still
        in `proposal` isn't taken at all, so approve it first. A range holding
        more than 100 such posts fails with a 422; schedule it in smaller
        ranges.


        Placing a post can fail for reasons this endpoint can't check up front,
        and each one is counted in the job's `result` rather than failing the
        request:


        - The workspace is on the free plan. Publishing scheduled posts needs a
        paid workspace plan, and those posts are counted in `plan_limited`.

        - The app has no connected account for the post's platform with
        publishing permission, or it has more than one. Those posts move to
        `needs_reconnect` and are counted there, and a later run picks them up
        once you fix the connection.

        - The post's platform can't be published to at all, or its scheduled
        time has already passed. Those posts move to `failed`, which is final.


        The social calendar endpoints share two rate limits: 20 requests per
        minute across creating, editing, deleting and approving posts, and 40
        requests per minute across the rest. This endpoint counts against the
        40.


        <Note>This endpoint accepts a personal API key. Workspace API keys are
        not authorized for it and are rejected with a 403.</Note>
      operationId: schedule_posts_api_apps__app_id__social_calendar_posts_schedule_post
      parameters:
        - name: app_id
          in: path
          required: true
          schema:
            type: string
            description: ID of the app whose social calendar you want.
            title: App Id
          description: ID of the app whose social calendar you want.
          example: 6820f3a4e7b91d003c45a1f2
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/SchedulePostsRequest'
      responses:
        '202':
          description: >-
            The scheduling job that is now running, or the one already in flight
            for this range.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SchedulePostsResponse'
        '401':
          description: Missing or invalid credentials.
        '403':
          description: >-
            You don't have editor access to this app, or you used a workspace
            API key.
        '404':
          description: >-
            App not found, or the social calendar is not enabled for your
            account.
        '409':
          description: Scheduling is already starting for this app. Retry the request.
        '422':
          description: Validation Error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/HTTPValidationError'
        '429':
          description: Rate limit exceeded (40 requests per minute).
components:
  schemas:
    SchedulePostsRequest:
      properties:
        scheduled_from:
          type: string
          format: date-time
          title: Scheduled From
          description: >-
            Start of the range to schedule, inclusive, as an ISO 8601 timestamp
            carrying an offset. A timestamp without one fails with a 422.
          example: '2026-09-01T00:00:00Z'
        scheduled_until:
          type: string
          format: date-time
          title: Scheduled Until
          description: >-
            End of the range, exclusive, as an ISO 8601 timestamp carrying an
            offset. It has to be later than `scheduled_from`.
          example: '2026-10-01T00:00:00Z'
      additionalProperties: false
      type: object
      required:
        - scheduled_from
        - scheduled_until
      title: SchedulePostsRequest
    SchedulePostsResponse:
      properties:
        job_id:
          type: string
          title: Job Id
          description: >-
            ID of the scheduling job. Pass it as `job_id` to [Get scheduling
            job](/api-reference/get-scheduling-job).
          example: 68a1c4f0d21b4e0a3c77e912
        status:
          type: string
          title: Status
          description: >-
            State of the job: `pending` before it starts, `running` while it
            hands posts over, then `completed` or `failed`. A range holding
            nothing to schedule comes back `completed` straight away.
          example: pending
      type: object
      required:
        - job_id
        - status
      title: SchedulePostsResponse
    HTTPValidationError:
      properties:
        detail:
          items:
            $ref: '#/components/schemas/ValidationError'
          type: array
          title: Detail
      type: object
      title: HTTPValidationError
    ValidationError:
      properties:
        loc:
          items:
            anyOf:
              - type: string
              - type: integer
          type: array
          title: Location
        msg:
          type: string
          title: Message
        type:
          type: string
          title: Error Type
      type: object
      required:
        - loc
        - msg
        - type
      title: ValidationError
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: api_key
      description: Personal API key.

````