northlight_sdk 0.7.15
northlight_sdk: ^0.7.15 copied to clipboard
Flutter SDK for Northlight feedback and bug reporting system. Collect user feedback, bug reports, and display roadmaps in your Flutter apps.
example/lib/main.dart
import 'package:flutter/material.dart';
import 'package:northlight_sdk/northlight_sdk.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Northlight SDK Demo',
theme: ThemeData(
colorScheme: ColorScheme.fromSeed(seedColor: Colors.blue),
useMaterial3: true,
),
home: const HomePage(),
);
}
}
class HomePage extends StatefulWidget {
const HomePage({super.key});
@override
State<HomePage> createState() => _HomePageState();
}
class _HomePageState extends State<HomePage> {
bool _isConfigured = false;
String? _lastSubmittedId;
@override
void initState() {
super.initState();
_initializeSDK();
}
Future<void> _initializeSDK() async {
try {
// Replace with your actual API key
await Northlight.configure('proj_54ccf17e-22ae-4690-a');
// Optional: Set user identification
await Northlight.setUserIdentifier('user_123');
await Northlight.setUserEmail('[email protected]');
setState(() {
_isConfigured = true;
});
} catch (e) {
_showError(e.toString());
}
}
void _showError(String message) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: Text(message),
backgroundColor: Colors.red,
),
);
}
void _showSuccess(String message) {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(
content: Text(message),
backgroundColor: Colors.green,
),
);
}
Future<void> _submitFeedbackProgrammatically() async {
try {
final feedbackId = await Northlight.submitFeedback(
title: 'Feature Request from Flutter',
description: 'This is a test feature request submitted programmatically',
category: 'enhancement',
);
setState(() {
_lastSubmittedId = feedbackId;
});
_showSuccess('Feedback submitted! ID: $feedbackId');
} catch (e) {
_showError(e.toString());
}
}
Future<void> _reportBugProgrammatically() async {
try {
final bugId = await Northlight.reportBug(
title: 'Bug Report from Flutter',
description: 'This is a test bug report',
severity: BugSeverity.medium,
stepsToReproduce: '1. Open app\n2. Click button\n3. See error',
);
setState(() {
_lastSubmittedId = bugId;
});
_showSuccess('Bug reported! ID: $bugId');
} catch (e) {
_showError(e.toString());
}
}
Future<void> _fetchPublicFeedback() async {
try {
final feedback = await Northlight.getPublicFeedback();
if (!mounted) return;
showDialog(
context: context,
builder: (context) => AlertDialog(
title: const Text('Public Feedback'),
content: SingleChildScrollView(
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
Text('Found ${feedback.length} feedback items'),
const SizedBox(height: 16),
...feedback.take(5).map((item) => Padding(
padding: const EdgeInsets.only(bottom: 8),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text('• ${item.title} (${item.voteCount} votes)'),
const SizedBox(height: 4),
Padding(
padding: const EdgeInsets.only(left: 16),
child: ElevatedButton(
onPressed: () async {
Navigator.of(context).pop();
await _voteOnFeedback(item.id);
},
child: const Text('Vote'),
),
),
],
),
)),
if (feedback.length > 5)
Text('... and ${feedback.length - 5} more'),
],
),
),
actions: [
TextButton(
onPressed: () => Navigator.of(context).pop(),
child: const Text('Close'),
),
],
),
);
} catch (e) {
_showError(e.toString());
}
}
Future<void> _voteOnFeedback(String feedbackId) async {
try {
final newVoteCount = await Northlight.vote(feedbackId);
_showSuccess('Vote submitted! New vote count: $newVoteCount');
} catch (e) {
_showError(e.toString());
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
backgroundColor: Theme.of(context).colorScheme.inversePrimary,
title: const Text('Northlight SDK Demo'),
),
body: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Card(
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
children: [
Row(
children: [
Icon(
_isConfigured ? Icons.check_circle : Icons.error,
color: _isConfigured ? Colors.green : Colors.red,
),
const SizedBox(width: 8),
Text(
_isConfigured ? 'SDK Configured' : 'SDK Not Configured',
style: Theme.of(context).textTheme.titleMedium,
),
],
),
if (_lastSubmittedId != null) ...[
const SizedBox(height: 8),
Text('Last submission ID: $_lastSubmittedId'),
],
],
),
),
),
const SizedBox(height: 16),
const Text(
'UI Presentation Methods',
style: TextStyle(fontSize: 18, fontWeight: FontWeight.bold),
),
const SizedBox(height: 8),
ElevatedButton.icon(
onPressed: _isConfigured ? () => Northlight.presentBugReportView() : null,
icon: const Icon(Icons.bug_report),
label: const Text('Present Bug Report View'),
),
const SizedBox(height: 8),
ElevatedButton.icon(
onPressed: _isConfigured ? () => Northlight.presentFeedbackView() : null,
icon: const Icon(Icons.feedback),
label: const Text('Present Feedback View'),
),
const SizedBox(height: 8),
ElevatedButton.icon(
onPressed: _isConfigured ? () => Northlight.presentPublicFeedbackView() : null,
icon: const Icon(Icons.list),
label: const Text('Present Public Feedback View'),
),
const SizedBox(height: 8),
ElevatedButton.icon(
onPressed: _isConfigured ? () => Northlight.presentRoadmapView() : null,
icon: const Icon(Icons.map),
label: const Text('Present Roadmap View'),
),
const SizedBox(height: 24),
const Text(
'Programmatic API',
style: TextStyle(fontSize: 18, fontWeight: FontWeight.bold),
),
const SizedBox(height: 8),
OutlinedButton.icon(
onPressed: _isConfigured ? _submitFeedbackProgrammatically : null,
icon: const Icon(Icons.send),
label: const Text('Submit Feedback Programmatically'),
),
const SizedBox(height: 8),
OutlinedButton.icon(
onPressed: _isConfigured ? _reportBugProgrammatically : null,
icon: const Icon(Icons.report),
label: const Text('Report Bug Programmatically'),
),
const SizedBox(height: 8),
OutlinedButton.icon(
onPressed: _isConfigured ? _fetchPublicFeedback : null,
icon: const Icon(Icons.download),
label: const Text('Fetch Public Feedback'),
),
],
),
),
);
}
}