createContainerFile method
Create a container file either by uploading raw bytes (multipart)
or by referencing an existing OpenAI File with fileId
.
Exactly one of (bytes
+ filename
) or fileId
must be provided.
// via file_id:
await client.createContainerFile(containerId: cid, fileId: 'file_abc123');
// via upload:
await client.createContainerFile(containerId: cid, bytes: data, filename: 'example.txt');
Implementation
Future<ContainerFile> createContainerFile({
required String containerId,
Uint8List? bytes,
String? filename,
String? fileId,
}) async {
if ((bytes == null || filename == null) && fileId == null) {
throw ArgumentError('Provide either (bytes + filename) or fileId.');
}
if ((bytes != null || filename != null) && fileId != null) {
throw ArgumentError('Provide only one of (bytes + filename) OR fileId, not both.');
}
// JSON route with file_id
if (fileId != null) {
final resp = await postJson('/containers/$containerId/files', {'file_id': fileId});
if (resp.statusCode == 200 || resp.statusCode == 201) {
return ContainerFile.fromJson(jsonDecode(resp.body) as Map<String, dynamic>);
}
throw OpenAIRequestException.fromHttpResponse(resp);
}
// Multipart upload route
final url = _resolve('/containers/$containerId/files');
final req = http.MultipartRequest('POST', url)
..headers.addAll(getHeaders({}) ?? {})
..files.add(http.MultipartFile.fromBytes('file', bytes!, filename: filename));
final streamed = await httpClient.send(req);
final body = await streamed.stream.bytesToString();
if (streamed.statusCode >= 200 && streamed.statusCode < 300) {
return ContainerFile.fromJson(jsonDecode(body) as Map<String, dynamic>);
}
// Synthesize an http.Response for consistent exception handling.
final asResponse = http.Response(body, streamed.statusCode, headers: streamed.headers, reasonPhrase: streamed.reasonPhrase);
throw OpenAIRequestException.fromHttpResponse(asResponse);
}