runapi-heygen-video 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 RunAPI
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,45 @@
1
+ Metadata-Version: 2.5
2
+ Name: runapi-heygen-video
3
+ Version: 0.1.0
4
+ Summary: RunAPI HeyGen Video SDK for text-to-video, reference-guided, and image-to-video workflows with generated sound in JavaScript, Python, Ruby, Go, Java, and PHP
5
+ Project-URL: Homepage, https://runapi.ai/models/heygen-video
6
+ Project-URL: Documentation, https://runapi.ai/docs/resources/sdks
7
+ Project-URL: Source, https://github.com/runapi-ai/heygen-video-sdk
8
+ Project-URL: Issues, https://github.com/runapi-ai/heygen-video-sdk/issues
9
+ Project-URL: Changelog, https://github.com/runapi-ai/heygen-video-sdk/blob/main/CHANGELOG.md
10
+ Project-URL: Release Notes, https://github.com/runapi-ai/heygen-video-sdk/releases/tag/python%2Fv0.1.0
11
+ Author-email: RunAPI <contact@runapi.ai>
12
+ License-Expression: Apache-2.0
13
+ License-File: LICENSE
14
+ Keywords: api,golang,gradle,heygen-video,image-to-video,java,maven,python,ruby,runapi,runapi-ai,sdk,text-to-video,typescript,video-generation
15
+ Requires-Python: >=3.9
16
+ Requires-Dist: runapi-core~=0.10.1
17
+ Description-Content-Type: text/markdown
18
+
19
+ # HeyGen Video API Python SDK for RunAPI
20
+
21
+ Use `runapi-heygen-video` for HeyGen Video video tasks in Python.
22
+
23
+ ```bash
24
+ pip install runapi-heygen-video
25
+ ```
26
+
27
+ ```python
28
+ from runapi.heygen_video import HeyGenVideoClient
29
+
30
+ client = HeyGenVideoClient()
31
+ result = client.text_to_video.run(
32
+ model="heygen-video-1",
33
+ prompt="A cinematic tracking shot through a rain-soaked city",
34
+ aspect_ratio="16:9",
35
+ )
36
+ print(result.videos[0].url)
37
+ ```
38
+
39
+ Use `text_to_video` for prompt-only or reference-media generation. Use `image_to_video` with a first-frame image. Each resource provides `create`, `get`, and `run`.
40
+
41
+ - [Model reference](https://runapi.ai/models/heygen-video)
42
+ - [API reference](https://runapi.ai/docs/api/heygen-video/text-to-video)
43
+ - [Pricing and rate limits](https://runapi.ai/models/heygen-video)
44
+
45
+ Licensed under the Apache License, Version 2.0.
@@ -0,0 +1,27 @@
1
+ # HeyGen Video API Python SDK for RunAPI
2
+
3
+ Use `runapi-heygen-video` for HeyGen Video video tasks in Python.
4
+
5
+ ```bash
6
+ pip install runapi-heygen-video
7
+ ```
8
+
9
+ ```python
10
+ from runapi.heygen_video import HeyGenVideoClient
11
+
12
+ client = HeyGenVideoClient()
13
+ result = client.text_to_video.run(
14
+ model="heygen-video-1",
15
+ prompt="A cinematic tracking shot through a rain-soaked city",
16
+ aspect_ratio="16:9",
17
+ )
18
+ print(result.videos[0].url)
19
+ ```
20
+
21
+ Use `text_to_video` for prompt-only or reference-media generation. Use `image_to_video` with a first-frame image. Each resource provides `create`, `get`, and `run`.
22
+
23
+ - [Model reference](https://runapi.ai/models/heygen-video)
24
+ - [API reference](https://runapi.ai/docs/api/heygen-video/text-to-video)
25
+ - [Pricing and rate limits](https://runapi.ai/models/heygen-video)
26
+
27
+ Licensed under the Apache License, Version 2.0.
@@ -0,0 +1,34 @@
1
+ [build-system]
2
+ requires = ["hatchling"]
3
+ build-backend = "hatchling.build"
4
+
5
+ [project]
6
+ name = "runapi-heygen-video"
7
+ version = "0.1.0"
8
+ description = "RunAPI HeyGen Video SDK for text-to-video, reference-guided, and image-to-video workflows with generated sound in JavaScript, Python, Ruby, Go, Java, and PHP"
9
+ readme = "README.md"
10
+ requires-python = ">=3.9"
11
+ license = "Apache-2.0"
12
+ authors = [{ name = "RunAPI", email = "contact@runapi.ai" }]
13
+ keywords = ["runapi", "runapi-ai", "heygen-video", "api", "sdk", "typescript", "python", "ruby", "golang", "java", "maven", "gradle", "video-generation", "text-to-video", "image-to-video"]
14
+ dependencies = ["runapi-core~=0.10.1"]
15
+
16
+ [project.urls]
17
+ Homepage = "https://runapi.ai/models/heygen-video"
18
+ Documentation = "https://runapi.ai/docs/resources/sdks"
19
+ Source = "https://github.com/runapi-ai/heygen-video-sdk"
20
+ Issues = "https://github.com/runapi-ai/heygen-video-sdk/issues"
21
+ Changelog = "https://github.com/runapi-ai/heygen-video-sdk/blob/main/CHANGELOG.md"
22
+ "Release Notes" = "https://github.com/runapi-ai/heygen-video-sdk/releases/tag/python%2Fv0.1.0"
23
+
24
+ [tool.hatch.build.targets.wheel]
25
+ packages = ["src/runapi"]
26
+
27
+ [tool.uv]
28
+ package = true
29
+
30
+ [dependency-groups]
31
+ dev = ["pytest>=8"]
32
+
33
+ [tool.runapi]
34
+ slug = "heygen-video"
@@ -0,0 +1,24 @@
1
+ """HeyGen Video client for RunAPI."""
2
+
3
+ from runapi.core import (
4
+ AuthenticationError,
5
+ InsufficientCreditsError,
6
+ NotFoundError,
7
+ RateLimitError,
8
+ TaskFailedError,
9
+ TaskTimeoutError,
10
+ ValidationError,
11
+ )
12
+
13
+ from .client import HeyGenVideoClient
14
+
15
+ __all__ = [
16
+ "HeyGenVideoClient",
17
+ "AuthenticationError",
18
+ "RateLimitError",
19
+ "InsufficientCreditsError",
20
+ "NotFoundError",
21
+ "ValidationError",
22
+ "TaskFailedError",
23
+ "TaskTimeoutError",
24
+ ]
@@ -0,0 +1,28 @@
1
+ """HeyGen Video client."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from typing import Any, Optional
6
+
7
+ from runapi.core import ProviderClient
8
+
9
+ from .resources.image_to_video import ImageToVideo
10
+ from .resources.text_to_video import TextToVideo
11
+
12
+
13
+ class HeyGenVideoClient(ProviderClient):
14
+ """HeyGen Video text-to-video and image-to-video client.
15
+
16
+ Example::
17
+
18
+ client = HeyGenVideoClient(api_key="sk-...")
19
+ result = client.text_to_video.run(
20
+ model="heygen-video-1", prompt="A neon city street"
21
+ )
22
+ """
23
+
24
+ def __init__(self, api_key: Optional[str] = None, **options: Any) -> None:
25
+ super().__init__(api_key, **options)
26
+ http = self._http
27
+ self.text_to_video = TextToVideo(http)
28
+ self.image_to_video = ImageToVideo(http)
@@ -0,0 +1,4 @@
1
+ from .image_to_video import ImageToVideo
2
+ from .text_to_video import TextToVideo
3
+
4
+ __all__ = ["TextToVideo", "ImageToVideo"]
@@ -0,0 +1,56 @@
1
+ """HeyGen Video image-to-video resource."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from typing import Any, Optional
6
+
7
+ from runapi.core import Resource, RequestOptions
8
+
9
+ from ..types import (
10
+ CompletedVideoTaskResponse,
11
+ VideoTaskResponse,
12
+ )
13
+
14
+
15
+ class ImageToVideo(Resource):
16
+ """Generate videos from a source image with HeyGen Video models."""
17
+
18
+ ENDPOINT = "/api/v1/heygen_video/image_to_video"
19
+
20
+ RESPONSE_CLASS = VideoTaskResponse
21
+ COMPLETED_RESPONSE_CLASS = CompletedVideoTaskResponse
22
+
23
+ def run(self, options: Optional[RequestOptions] = None, **params: Any) -> Any:
24
+ """Create an image-to-video task and poll until it completes.
25
+
26
+ Args:
27
+ **params: Image-to-video parameters (model, prompt, ...).
28
+
29
+ Returns:
30
+ The completed task with videos.
31
+ """
32
+ task = self.create(options=options, **params)
33
+ return self._poll_until_complete(lambda: self.get(task.id, options=options))
34
+
35
+ def create(self, options: Optional[RequestOptions] = None, **params: Any) -> Any:
36
+ """Create an image-to-video task and return immediately with an ``id``.
37
+
38
+ Args:
39
+ **params: Image-to-video parameters (model, prompt, ...).
40
+
41
+ Returns:
42
+ The task creation result with an id.
43
+ """
44
+ compacted = self._compact_params(params)
45
+ return self._request("post", self.ENDPOINT, body=compacted, options=options)
46
+
47
+ def get(self, id: str, options: Optional[RequestOptions] = None) -> Any:
48
+ """Fetch the current status of an image-to-video task.
49
+
50
+ Args:
51
+ id: The task id.
52
+
53
+ Returns:
54
+ The current task status.
55
+ """
56
+ return self._request("get", f"{self.ENDPOINT}/{id}", options=options)
@@ -0,0 +1,56 @@
1
+ """HeyGen Video text-to-video resource."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from typing import Any, Optional
6
+
7
+ from runapi.core import Resource, RequestOptions
8
+
9
+ from ..types import (
10
+ CompletedVideoTaskResponse,
11
+ VideoTaskResponse,
12
+ )
13
+
14
+
15
+ class TextToVideo(Resource):
16
+ """Generate videos from text prompts with HeyGen Video models."""
17
+
18
+ ENDPOINT = "/api/v1/heygen_video/text_to_video"
19
+
20
+ RESPONSE_CLASS = VideoTaskResponse
21
+ COMPLETED_RESPONSE_CLASS = CompletedVideoTaskResponse
22
+
23
+ def run(self, options: Optional[RequestOptions] = None, **params: Any) -> Any:
24
+ """Create a text-to-video task and poll until it completes.
25
+
26
+ Args:
27
+ **params: Text-to-video parameters (model, prompt, ...).
28
+
29
+ Returns:
30
+ The completed task with videos.
31
+ """
32
+ task = self.create(options=options, **params)
33
+ return self._poll_until_complete(lambda: self.get(task.id, options=options))
34
+
35
+ def create(self, options: Optional[RequestOptions] = None, **params: Any) -> Any:
36
+ """Create a text-to-video task and return immediately with an ``id``.
37
+
38
+ Args:
39
+ **params: Text-to-video parameters (model, prompt, ...).
40
+
41
+ Returns:
42
+ The task creation result with an id.
43
+ """
44
+ compacted = self._compact_params(params)
45
+ return self._request("post", self.ENDPOINT, body=compacted, options=options)
46
+
47
+ def get(self, id: str, options: Optional[RequestOptions] = None) -> Any:
48
+ """Fetch the current status of a text-to-video task.
49
+
50
+ Args:
51
+ id: The task id.
52
+
53
+ Returns:
54
+ The current task status.
55
+ """
56
+ return self._request("get", f"{self.ENDPOINT}/{id}", options=options)
@@ -0,0 +1,24 @@
1
+ """HeyGen Video model lists, enums, and response models."""
2
+
3
+ from __future__ import annotations
4
+
5
+ from runapi.core import BaseModel, TaskResponse, optional, required
6
+
7
+
8
+ class MediaUrl(BaseModel):
9
+ url = optional(str)
10
+
11
+
12
+ class VideoTaskResponse(TaskResponse):
13
+ """Response for a video generation task."""
14
+
15
+ id = required(str)
16
+ status = optional(str, enum=lambda: TaskResponse.Status.ALL)
17
+ videos = optional([lambda: MediaUrl])
18
+ error = optional(str)
19
+
20
+
21
+ class CompletedVideoTaskResponse(VideoTaskResponse):
22
+ """Narrowed response from ``run()`` once polling observes completion."""
23
+
24
+ videos = required([lambda: MediaUrl])
@@ -0,0 +1,47 @@
1
+ from runapi.heygen_video import HeyGenVideoClient
2
+
3
+
4
+ class FakeHttp:
5
+ def __init__(self, response=None):
6
+ self.response = response or {"id": "task_1", "status": "pending"}
7
+ self.calls = []
8
+
9
+ def request(self, method, path, body=None, options=None):
10
+ self.calls.append((method, path, body))
11
+ return self.response
12
+
13
+
14
+ def test_posts_reference_media_through_text_to_video():
15
+ fake = FakeHttp()
16
+ client = HeyGenVideoClient(api_key="k", http_client=fake)
17
+ client.text_to_video.create(
18
+ model="heygen-video-1",
19
+ prompt="Continue the performance",
20
+ reference_image_urls=["https://cdn.runapi.ai/public/samples/image.jpg"],
21
+ reference_audio_urls=["https://cdn.runapi.ai/public/samples/voice.mp3"],
22
+ aspect_ratio="adaptive",
23
+ )
24
+ assert fake.calls == [("post", "/api/v1/heygen_video/text_to_video", {
25
+ "model": "heygen-video-1",
26
+ "prompt": "Continue the performance",
27
+ "reference_image_urls": ["https://cdn.runapi.ai/public/samples/image.jpg"],
28
+ "reference_audio_urls": ["https://cdn.runapi.ai/public/samples/voice.mp3"],
29
+ "aspect_ratio": "adaptive",
30
+ })]
31
+
32
+
33
+ def test_posts_first_frame_and_seed_through_image_to_video():
34
+ fake = FakeHttp()
35
+ client = HeyGenVideoClient(api_key="k", http_client=fake)
36
+ client.image_to_video.create(
37
+ model="heygen-video-1",
38
+ prompt="Animate",
39
+ first_frame_image_url="https://cdn.runapi.ai/public/samples/image.jpg",
40
+ seed=42,
41
+ )
42
+ assert fake.calls == [("post", "/api/v1/heygen_video/image_to_video", {
43
+ "model": "heygen-video-1",
44
+ "prompt": "Animate",
45
+ "first_frame_image_url": "https://cdn.runapi.ai/public/samples/image.jpg",
46
+ "seed": 42,
47
+ })]