feat: make credentialsFilePath nullable in OAuth models and update related logic

This commit is contained in:
Udhay-Adithya
2025-08-06 11:43:56 +05:30
parent 71a98cd2e5
commit c0bb09fd35
10 changed files with 68 additions and 60 deletions

View File

@@ -1,11 +1,12 @@
import 'package:apidash/utils/utils.dart'; import 'package:apidash/providers/settings_providers.dart';
import 'package:apidash/widgets/widgets.dart'; import 'package:apidash/widgets/widgets.dart';
import 'package:apidash_core/apidash_core.dart'; import 'package:apidash_core/apidash_core.dart';
import 'package:apidash_design_system/widgets/widgets.dart'; import 'package:apidash_design_system/widgets/widgets.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'consts.dart'; import 'consts.dart';
class OAuth1Fields extends StatefulWidget { class OAuth1Fields extends ConsumerStatefulWidget {
final AuthModel? authData; final AuthModel? authData;
final bool readOnly; final bool readOnly;
@@ -20,10 +21,10 @@ class OAuth1Fields extends StatefulWidget {
}); });
@override @override
State<OAuth1Fields> createState() => _OAuth1FieldsState(); ConsumerState<OAuth1Fields> createState() => _OAuth1FieldsState();
} }
class _OAuth1FieldsState extends State<OAuth1Fields> { class _OAuth1FieldsState extends ConsumerState<OAuth1Fields> {
late TextEditingController _consumerKeyController; late TextEditingController _consumerKeyController;
late TextEditingController _consumerSecretController; late TextEditingController _consumerSecretController;
late TextEditingController _accessTokenController; late TextEditingController _accessTokenController;
@@ -61,8 +62,8 @@ class _OAuth1FieldsState extends State<OAuth1Fields> {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Column( return ListView(
crossAxisAlignment: CrossAxisAlignment.start, shrinkWrap: true,
children: [ children: [
// Text( // Text(
// "Add auth data to", // "Add auth data to",
@@ -198,12 +199,11 @@ class _OAuth1FieldsState extends State<OAuth1Fields> {
} }
void _updateOAuth1() async { void _updateOAuth1() async {
final String? credentialsFilePath = final settingsModel = ref.read(settingsProvider);
await getApplicationSupportDirectoryFilePath( final credentialsFilePath = settingsModel.workspaceFolderPath != null
"oauth1_credentials", "json"); ? "${settingsModel.workspaceFolderPath}/oauth1_credentials.json"
if (credentialsFilePath == null) { : null;
return;
}
widget.updateAuth?.call( widget.updateAuth?.call(
widget.authData?.copyWith( widget.authData?.copyWith(
type: APIAuthType.oauth1, type: APIAuthType.oauth1,

View File

@@ -384,9 +384,6 @@ class _OAuth2FieldsState extends ConsumerState<OAuth2Fields> {
void _updateOAuth2() async { void _updateOAuth2() async {
final String? credentialsFilePath = final String? credentialsFilePath =
ref.read(settingsProvider).workspaceFolderPath; ref.read(settingsProvider).workspaceFolderPath;
if (credentialsFilePath == null) {
return;
}
final updatedOAuth2 = AuthOAuth2Model( final updatedOAuth2 = AuthOAuth2Model(
grantType: _grantType, grantType: _grantType,
@@ -394,7 +391,9 @@ class _OAuth2FieldsState extends ConsumerState<OAuth2Fields> {
clientId: _clientIdController.text.trim(), clientId: _clientIdController.text.trim(),
accessTokenUrl: _accessTokenUrlController.text.trim(), accessTokenUrl: _accessTokenUrlController.text.trim(),
clientSecret: _clientSecretController.text.trim(), clientSecret: _clientSecretController.text.trim(),
credentialsFilePath: "$credentialsFilePath/oauth2_credentials.json", credentialsFilePath: credentialsFilePath != null
? "$credentialsFilePath/oauth2_credentials.json"
: null,
codeChallengeMethod: _codeChallengeMethod, codeChallengeMethod: _codeChallengeMethod,
redirectUrl: _redirectUrlController.text.trim(), redirectUrl: _redirectUrlController.text.trim(),
scope: _scopeController.text.trim(), scope: _scopeController.text.trim(),

View File

@@ -10,10 +10,11 @@ class AuthOAuth1Model with _$AuthOAuth1Model {
const factory AuthOAuth1Model({ const factory AuthOAuth1Model({
required String consumerKey, required String consumerKey,
required String consumerSecret, required String consumerSecret,
required String credentialsFilePath, String? credentialsFilePath,
String? accessToken, String? accessToken,
String? tokenSecret, String? tokenSecret,
@Default(OAuth1SignatureMethod.hmacSha1) OAuth1SignatureMethod signatureMethod, @Default(OAuth1SignatureMethod.hmacSha1)
OAuth1SignatureMethod signatureMethod,
@Default("header") String parameterLocation, @Default("header") String parameterLocation,
@Default('1.0') String version, @Default('1.0') String version,
String? realm, String? realm,

View File

@@ -23,7 +23,7 @@ AuthOAuth1Model _$AuthOAuth1ModelFromJson(Map<String, dynamic> json) {
mixin _$AuthOAuth1Model { mixin _$AuthOAuth1Model {
String get consumerKey => throw _privateConstructorUsedError; String get consumerKey => throw _privateConstructorUsedError;
String get consumerSecret => throw _privateConstructorUsedError; String get consumerSecret => throw _privateConstructorUsedError;
String get credentialsFilePath => throw _privateConstructorUsedError; String? get credentialsFilePath => throw _privateConstructorUsedError;
String? get accessToken => throw _privateConstructorUsedError; String? get accessToken => throw _privateConstructorUsedError;
String? get tokenSecret => throw _privateConstructorUsedError; String? get tokenSecret => throw _privateConstructorUsedError;
OAuth1SignatureMethod get signatureMethod => OAuth1SignatureMethod get signatureMethod =>
@@ -57,7 +57,7 @@ abstract class $AuthOAuth1ModelCopyWith<$Res> {
$Res call({ $Res call({
String consumerKey, String consumerKey,
String consumerSecret, String consumerSecret,
String credentialsFilePath, String? credentialsFilePath,
String? accessToken, String? accessToken,
String? tokenSecret, String? tokenSecret,
OAuth1SignatureMethod signatureMethod, OAuth1SignatureMethod signatureMethod,
@@ -89,7 +89,7 @@ class _$AuthOAuth1ModelCopyWithImpl<$Res, $Val extends AuthOAuth1Model>
$Res call({ $Res call({
Object? consumerKey = null, Object? consumerKey = null,
Object? consumerSecret = null, Object? consumerSecret = null,
Object? credentialsFilePath = null, Object? credentialsFilePath = freezed,
Object? accessToken = freezed, Object? accessToken = freezed,
Object? tokenSecret = freezed, Object? tokenSecret = freezed,
Object? signatureMethod = null, Object? signatureMethod = null,
@@ -112,10 +112,10 @@ class _$AuthOAuth1ModelCopyWithImpl<$Res, $Val extends AuthOAuth1Model>
? _value.consumerSecret ? _value.consumerSecret
: consumerSecret // ignore: cast_nullable_to_non_nullable : consumerSecret // ignore: cast_nullable_to_non_nullable
as String, as String,
credentialsFilePath: null == credentialsFilePath credentialsFilePath: freezed == credentialsFilePath
? _value.credentialsFilePath ? _value.credentialsFilePath
: credentialsFilePath // ignore: cast_nullable_to_non_nullable : credentialsFilePath // ignore: cast_nullable_to_non_nullable
as String, as String?,
accessToken: freezed == accessToken accessToken: freezed == accessToken
? _value.accessToken ? _value.accessToken
: accessToken // ignore: cast_nullable_to_non_nullable : accessToken // ignore: cast_nullable_to_non_nullable
@@ -178,7 +178,7 @@ abstract class _$$AuthOAuth1ModelImplCopyWith<$Res>
$Res call({ $Res call({
String consumerKey, String consumerKey,
String consumerSecret, String consumerSecret,
String credentialsFilePath, String? credentialsFilePath,
String? accessToken, String? accessToken,
String? tokenSecret, String? tokenSecret,
OAuth1SignatureMethod signatureMethod, OAuth1SignatureMethod signatureMethod,
@@ -209,7 +209,7 @@ class __$$AuthOAuth1ModelImplCopyWithImpl<$Res>
$Res call({ $Res call({
Object? consumerKey = null, Object? consumerKey = null,
Object? consumerSecret = null, Object? consumerSecret = null,
Object? credentialsFilePath = null, Object? credentialsFilePath = freezed,
Object? accessToken = freezed, Object? accessToken = freezed,
Object? tokenSecret = freezed, Object? tokenSecret = freezed,
Object? signatureMethod = null, Object? signatureMethod = null,
@@ -232,10 +232,10 @@ class __$$AuthOAuth1ModelImplCopyWithImpl<$Res>
? _value.consumerSecret ? _value.consumerSecret
: consumerSecret // ignore: cast_nullable_to_non_nullable : consumerSecret // ignore: cast_nullable_to_non_nullable
as String, as String,
credentialsFilePath: null == credentialsFilePath credentialsFilePath: freezed == credentialsFilePath
? _value.credentialsFilePath ? _value.credentialsFilePath
: credentialsFilePath // ignore: cast_nullable_to_non_nullable : credentialsFilePath // ignore: cast_nullable_to_non_nullable
as String, as String?,
accessToken: freezed == accessToken accessToken: freezed == accessToken
? _value.accessToken ? _value.accessToken
: accessToken // ignore: cast_nullable_to_non_nullable : accessToken // ignore: cast_nullable_to_non_nullable
@@ -291,7 +291,7 @@ class _$AuthOAuth1ModelImpl implements _AuthOAuth1Model {
const _$AuthOAuth1ModelImpl({ const _$AuthOAuth1ModelImpl({
required this.consumerKey, required this.consumerKey,
required this.consumerSecret, required this.consumerSecret,
required this.credentialsFilePath, this.credentialsFilePath,
this.accessToken, this.accessToken,
this.tokenSecret, this.tokenSecret,
this.signatureMethod = OAuth1SignatureMethod.hmacSha1, this.signatureMethod = OAuth1SignatureMethod.hmacSha1,
@@ -313,7 +313,7 @@ class _$AuthOAuth1ModelImpl implements _AuthOAuth1Model {
@override @override
final String consumerSecret; final String consumerSecret;
@override @override
final String credentialsFilePath; final String? credentialsFilePath;
@override @override
final String? accessToken; final String? accessToken;
@override @override
@@ -419,7 +419,7 @@ abstract class _AuthOAuth1Model implements AuthOAuth1Model {
const factory _AuthOAuth1Model({ const factory _AuthOAuth1Model({
required final String consumerKey, required final String consumerKey,
required final String consumerSecret, required final String consumerSecret,
required final String credentialsFilePath, final String? credentialsFilePath,
final String? accessToken, final String? accessToken,
final String? tokenSecret, final String? tokenSecret,
final OAuth1SignatureMethod signatureMethod, final OAuth1SignatureMethod signatureMethod,
@@ -441,7 +441,7 @@ abstract class _AuthOAuth1Model implements AuthOAuth1Model {
@override @override
String get consumerSecret; String get consumerSecret;
@override @override
String get credentialsFilePath; String? get credentialsFilePath;
@override @override
String? get accessToken; String? get accessToken;
@override @override

View File

@@ -11,7 +11,7 @@ _$AuthOAuth1ModelImpl _$$AuthOAuth1ModelImplFromJson(
) => _$AuthOAuth1ModelImpl( ) => _$AuthOAuth1ModelImpl(
consumerKey: json['consumerKey'] as String, consumerKey: json['consumerKey'] as String,
consumerSecret: json['consumerSecret'] as String, consumerSecret: json['consumerSecret'] as String,
credentialsFilePath: json['credentialsFilePath'] as String, credentialsFilePath: json['credentialsFilePath'] as String?,
accessToken: json['accessToken'] as String?, accessToken: json['accessToken'] as String?,
tokenSecret: json['tokenSecret'] as String?, tokenSecret: json['tokenSecret'] as String?,
signatureMethod: signatureMethod:

View File

@@ -13,7 +13,7 @@ class AuthOAuth2Model with _$AuthOAuth2Model {
required String accessTokenUrl, required String accessTokenUrl,
required String clientId, required String clientId,
required String clientSecret, required String clientSecret,
required String credentialsFilePath, String? credentialsFilePath,
String? redirectUrl, String? redirectUrl,
String? scope, String? scope,
String? state, String? state,

View File

@@ -26,7 +26,7 @@ mixin _$AuthOAuth2Model {
String get accessTokenUrl => throw _privateConstructorUsedError; String get accessTokenUrl => throw _privateConstructorUsedError;
String get clientId => throw _privateConstructorUsedError; String get clientId => throw _privateConstructorUsedError;
String get clientSecret => throw _privateConstructorUsedError; String get clientSecret => throw _privateConstructorUsedError;
String get credentialsFilePath => throw _privateConstructorUsedError; String? get credentialsFilePath => throw _privateConstructorUsedError;
String? get redirectUrl => throw _privateConstructorUsedError; String? get redirectUrl => throw _privateConstructorUsedError;
String? get scope => throw _privateConstructorUsedError; String? get scope => throw _privateConstructorUsedError;
String? get state => throw _privateConstructorUsedError; String? get state => throw _privateConstructorUsedError;
@@ -62,7 +62,7 @@ abstract class $AuthOAuth2ModelCopyWith<$Res> {
String accessTokenUrl, String accessTokenUrl,
String clientId, String clientId,
String clientSecret, String clientSecret,
String credentialsFilePath, String? credentialsFilePath,
String? redirectUrl, String? redirectUrl,
String? scope, String? scope,
String? state, String? state,
@@ -97,7 +97,7 @@ class _$AuthOAuth2ModelCopyWithImpl<$Res, $Val extends AuthOAuth2Model>
Object? accessTokenUrl = null, Object? accessTokenUrl = null,
Object? clientId = null, Object? clientId = null,
Object? clientSecret = null, Object? clientSecret = null,
Object? credentialsFilePath = null, Object? credentialsFilePath = freezed,
Object? redirectUrl = freezed, Object? redirectUrl = freezed,
Object? scope = freezed, Object? scope = freezed,
Object? state = freezed, Object? state = freezed,
@@ -132,10 +132,10 @@ class _$AuthOAuth2ModelCopyWithImpl<$Res, $Val extends AuthOAuth2Model>
? _value.clientSecret ? _value.clientSecret
: clientSecret // ignore: cast_nullable_to_non_nullable : clientSecret // ignore: cast_nullable_to_non_nullable
as String, as String,
credentialsFilePath: null == credentialsFilePath credentialsFilePath: freezed == credentialsFilePath
? _value.credentialsFilePath ? _value.credentialsFilePath
: credentialsFilePath // ignore: cast_nullable_to_non_nullable : credentialsFilePath // ignore: cast_nullable_to_non_nullable
as String, as String?,
redirectUrl: freezed == redirectUrl redirectUrl: freezed == redirectUrl
? _value.redirectUrl ? _value.redirectUrl
: redirectUrl // ignore: cast_nullable_to_non_nullable : redirectUrl // ignore: cast_nullable_to_non_nullable
@@ -201,7 +201,7 @@ abstract class _$$AuthOAuth2ModelImplCopyWith<$Res>
String accessTokenUrl, String accessTokenUrl,
String clientId, String clientId,
String clientSecret, String clientSecret,
String credentialsFilePath, String? credentialsFilePath,
String? redirectUrl, String? redirectUrl,
String? scope, String? scope,
String? state, String? state,
@@ -235,7 +235,7 @@ class __$$AuthOAuth2ModelImplCopyWithImpl<$Res>
Object? accessTokenUrl = null, Object? accessTokenUrl = null,
Object? clientId = null, Object? clientId = null,
Object? clientSecret = null, Object? clientSecret = null,
Object? credentialsFilePath = null, Object? credentialsFilePath = freezed,
Object? redirectUrl = freezed, Object? redirectUrl = freezed,
Object? scope = freezed, Object? scope = freezed,
Object? state = freezed, Object? state = freezed,
@@ -270,10 +270,10 @@ class __$$AuthOAuth2ModelImplCopyWithImpl<$Res>
? _value.clientSecret ? _value.clientSecret
: clientSecret // ignore: cast_nullable_to_non_nullable : clientSecret // ignore: cast_nullable_to_non_nullable
as String, as String,
credentialsFilePath: null == credentialsFilePath credentialsFilePath: freezed == credentialsFilePath
? _value.credentialsFilePath ? _value.credentialsFilePath
: credentialsFilePath // ignore: cast_nullable_to_non_nullable : credentialsFilePath // ignore: cast_nullable_to_non_nullable
as String, as String?,
redirectUrl: freezed == redirectUrl redirectUrl: freezed == redirectUrl
? _value.redirectUrl ? _value.redirectUrl
: redirectUrl // ignore: cast_nullable_to_non_nullable : redirectUrl // ignore: cast_nullable_to_non_nullable
@@ -332,7 +332,7 @@ class _$AuthOAuth2ModelImpl implements _AuthOAuth2Model {
required this.accessTokenUrl, required this.accessTokenUrl,
required this.clientId, required this.clientId,
required this.clientSecret, required this.clientSecret,
required this.credentialsFilePath, this.credentialsFilePath,
this.redirectUrl, this.redirectUrl,
this.scope, this.scope,
this.state, this.state,
@@ -361,7 +361,7 @@ class _$AuthOAuth2ModelImpl implements _AuthOAuth2Model {
@override @override
final String clientSecret; final String clientSecret;
@override @override
final String credentialsFilePath; final String? credentialsFilePath;
@override @override
final String? redirectUrl; final String? redirectUrl;
@override @override
@@ -477,7 +477,7 @@ abstract class _AuthOAuth2Model implements AuthOAuth2Model {
required final String accessTokenUrl, required final String accessTokenUrl,
required final String clientId, required final String clientId,
required final String clientSecret, required final String clientSecret,
required final String credentialsFilePath, final String? credentialsFilePath,
final String? redirectUrl, final String? redirectUrl,
final String? scope, final String? scope,
final String? state, final String? state,
@@ -505,7 +505,7 @@ abstract class _AuthOAuth2Model implements AuthOAuth2Model {
@override @override
String get clientSecret; String get clientSecret;
@override @override
String get credentialsFilePath; String? get credentialsFilePath;
@override @override
String? get redirectUrl; String? get redirectUrl;
@override @override

View File

@@ -16,7 +16,7 @@ _$AuthOAuth2ModelImpl _$$AuthOAuth2ModelImplFromJson(
accessTokenUrl: json['accessTokenUrl'] as String, accessTokenUrl: json['accessTokenUrl'] as String,
clientId: json['clientId'] as String, clientId: json['clientId'] as String,
clientSecret: json['clientSecret'] as String, clientSecret: json['clientSecret'] as String,
credentialsFilePath: json['credentialsFilePath'] as String, credentialsFilePath: json['credentialsFilePath'] as String?,
redirectUrl: json['redirectUrl'] as String?, redirectUrl: json['redirectUrl'] as String?,
scope: json['scope'] as String?, scope: json['scope'] as String?,
state: json['state'] as String?, state: json['state'] as String?,

View File

@@ -188,7 +188,9 @@ Future<HttpRequestModel> handleAuth(
throw Exception("No Redirect URL found!"); throw Exception("No Redirect URL found!");
} }
final credentialsFile = File(oauth2.credentialsFilePath); final credentialsFile = oauth2.credentialsFilePath != null
? File(oauth2.credentialsFilePath!)
: null;
switch (oauth2.grantType) { switch (oauth2.grantType) {
case OAuth2GrantType.authorizationCode: case OAuth2GrantType.authorizationCode:

View File

@@ -20,12 +20,12 @@ Future<(oauth2.Client, OAuthCallbackServer?)> oAuth2AuthorizationCodeGrant({
required Uri authorizationEndpoint, required Uri authorizationEndpoint,
required Uri tokenEndpoint, required Uri tokenEndpoint,
required Uri redirectUrl, required Uri redirectUrl,
required File credentialsFile, required File? credentialsFile,
String? state, String? state,
String? scope, String? scope,
}) async { }) async {
// Check for existing valid credentials first // Check for existing credentials first
if (await credentialsFile.exists()) { if (credentialsFile != null && await credentialsFile.exists()) {
try { try {
final json = await credentialsFile.readAsString(); final json = await credentialsFile.readAsString();
final credentials = oauth2.Credentials.fromJson(json); final credentials = oauth2.Credentials.fromJson(json);
@@ -139,7 +139,9 @@ Future<(oauth2.Client, OAuthCallbackServer?)> oAuth2AuthorizationCodeGrant({
); );
log('OAuth2 authorization successful, saving credentials'); log('OAuth2 authorization successful, saving credentials');
await credentialsFile.writeAsString(client.credentials.toJson()); if (credentialsFile != null) {
await credentialsFile.writeAsString(client.credentials.toJson());
}
log(client.credentials.toJson()); log(client.credentials.toJson());
return (client, callbackServer); return (client, callbackServer);
@@ -166,10 +168,10 @@ Future<(oauth2.Client, OAuthCallbackServer?)> oAuth2AuthorizationCodeGrant({
Future<oauth2.Client> oAuth2ClientCredentialsGrantHandler({ Future<oauth2.Client> oAuth2ClientCredentialsGrantHandler({
required AuthOAuth2Model oauth2Model, required AuthOAuth2Model oauth2Model,
required File credentialsFile, required File? credentialsFile,
}) async { }) async {
// Try to use saved credentials // Try to use saved credentials
if (await credentialsFile.exists()) { if (credentialsFile != null && await credentialsFile.exists()) {
try { try {
final json = await credentialsFile.readAsString(); final json = await credentialsFile.readAsString();
final credentials = oauth2.Credentials.fromJson(json); final credentials = oauth2.Credentials.fromJson(json);
@@ -211,8 +213,10 @@ Future<oauth2.Client> oAuth2ClientCredentialsGrantHandler({
log('Successfully authenticated via client credentials grant'); log('Successfully authenticated via client credentials grant');
try { try {
await credentialsFile.writeAsString(client.credentials.toJson()); if (credentialsFile != null) {
log('Saved credentials to file'); await credentialsFile.writeAsString(client.credentials.toJson());
log('Saved credentials to file');
}
} catch (e) { } catch (e) {
log('Failed to save credentials: $e'); log('Failed to save credentials: $e');
} }
@@ -230,10 +234,10 @@ Future<oauth2.Client> oAuth2ClientCredentialsGrantHandler({
Future<oauth2.Client> oAuth2ResourceOwnerPasswordGrantHandler({ Future<oauth2.Client> oAuth2ResourceOwnerPasswordGrantHandler({
required AuthOAuth2Model oauth2Model, required AuthOAuth2Model oauth2Model,
required File credentialsFile, required File? credentialsFile,
}) async { }) async {
// Try to use saved credentials // Try to use saved credentials
if (await credentialsFile.exists()) { if (credentialsFile != null && await credentialsFile.exists()) {
try { try {
final json = await credentialsFile.readAsString(); final json = await credentialsFile.readAsString();
final credentials = oauth2.Credentials.fromJson(json); final credentials = oauth2.Credentials.fromJson(json);
@@ -281,8 +285,10 @@ Future<oauth2.Client> oAuth2ResourceOwnerPasswordGrantHandler({
log('Successfully authenticated via client credentials grant'); log('Successfully authenticated via client credentials grant');
try { try {
await credentialsFile.writeAsString(client.credentials.toJson()); if (credentialsFile != null) {
log('Saved credentials to file'); await credentialsFile.writeAsString(client.credentials.toJson());
log('Saved credentials to file');
}
} catch (e) { } catch (e) {
log('Failed to save credentials: $e'); log('Failed to save credentials: $e');
} }