Initial commit — DLS lab-app Flutter project
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
import 'dart:async';
|
||||
import 'dart:convert';
|
||||
import 'package:http/http.dart' as http;
|
||||
|
||||
class AiService {
|
||||
static const _baseUrl = 'https://api.featherless.ai/v1';
|
||||
static const _apiKey =
|
||||
'rc_e10f49aaa4f7af03dcd9da115cfc12cc1988665e895955c11f77788ee5ad93c6';
|
||||
static const _model = 'Qwen/Qwen2.5-7B-Instruct';
|
||||
|
||||
AiService._();
|
||||
static final instance = AiService._();
|
||||
|
||||
Stream<String> streamChat({
|
||||
required String systemPrompt,
|
||||
required List<Map<String, String>> messages,
|
||||
}) async* {
|
||||
final client = http.Client();
|
||||
try {
|
||||
final request = http.Request(
|
||||
'POST',
|
||||
Uri.parse('$_baseUrl/chat/completions'),
|
||||
);
|
||||
request.headers.addAll({
|
||||
'Authorization': 'Bearer $_apiKey',
|
||||
'Content-Type': 'application/json',
|
||||
});
|
||||
request.body = jsonEncode({
|
||||
'model': _model,
|
||||
'messages': [
|
||||
{'role': 'system', 'content': systemPrompt},
|
||||
...messages,
|
||||
],
|
||||
'stream': true,
|
||||
'max_tokens': 2048,
|
||||
'temperature': 0.7,
|
||||
});
|
||||
|
||||
final response = await client.send(request);
|
||||
if (response.statusCode != 200) {
|
||||
final body = await response.stream.bytesToString();
|
||||
String msg = 'API hatası ${response.statusCode}';
|
||||
try {
|
||||
final j = jsonDecode(body) as Map<String, dynamic>;
|
||||
msg = (j['error'] as Map?)?['message'] as String? ?? msg;
|
||||
} catch (_) {}
|
||||
throw Exception(msg);
|
||||
}
|
||||
|
||||
final lines = response.stream
|
||||
.transform(utf8.decoder)
|
||||
.transform(const LineSplitter());
|
||||
|
||||
await for (final line in lines) {
|
||||
if (!line.startsWith('data: ')) continue;
|
||||
final payload = line.substring(6).trim();
|
||||
if (payload == '[DONE]') break;
|
||||
try {
|
||||
final j = jsonDecode(payload) as Map<String, dynamic>;
|
||||
final choices = j['choices'] as List?;
|
||||
if (choices == null || choices.isEmpty) continue;
|
||||
final delta = choices.first['delta'] as Map<String, dynamic>?;
|
||||
final content = delta?['content'] as String?;
|
||||
if (content != null && content.isNotEmpty) yield content;
|
||||
} catch (_) {}
|
||||
}
|
||||
} finally {
|
||||
client.close();
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user