igot_http_service_helper

A Flutter package that provides a high-level HTTP service layer built on top of Dio. It supports TTL-based caching (powered by Hive), request deduplication, and configurable timeouts — designed for use in the iGOT Karmayogi project.

Migration note: As of v0.5.0 this package has migrated its underlying HTTP client from package:http to dio. The public HttpService API is unchanged; response objects are now dio.Response<dynamic> instead of http.Response.


Features

HTTP Methods

GET · POST · PUT · PATCH · DELETE · UPLOAD (multipart)

TTL-based Caching (Hive)

TTL value Behaviour
null Hits the API directly every time
provided Checks Hive cache first
— cached & within TTL Returns cached data
— cached & expired Calls API, refreshes cache, returns fresh data
— not in cache Calls API, stores result, returns response

Force Update

Set forceUpdate: true to bypass the cache and always fetch fresh data, then update the cache with the new response.

Request Deduplication

Concurrent identical requests are collapsed into a single in-flight network call.

Configurable Timeouts

Call HttpService.configure(...) once at startup to override connectTimeout, receiveTimeout, and sendTimeout.

SSL Certificate Pinning

Enable SSL pinning to protect against man-in-the-middle attacks. The library supports two pinning methods:

Method When to Use
Public Key Hash Pinning When publicKeyHashes is provided — validates SHA-256 hash of server's public key
Certificate Pinning When trustedCertificates is provided — validates against exact certificate

Note: If publicKeyHashes is provided, public key hash pinning takes priority. The library automatically selects the appropriate validation method based on your configuration.


Getting Started

Add the package to your pubspec.yaml:

dependencies:
  igot_http_service_helper:
    git:
      url: https://git.idc.tarento.com/igot/http_service

Note: dio is a transitive dependency — you do not need to add it separately unless you need to import Dio types (e.g. Response, ResponseType) directly in your own code.


Usage

Import

import 'package:igot_http_service_helper/services/http_service.dart';
import 'package:dio/dio.dart'; // only if you use Dio types directly

Optional one-time configuration

HttpService.configure(
  connectTimeout: const Duration(seconds: 10),
  receiveTimeout: const Duration(seconds: 30),
  sendTimeout:    const Duration(seconds: 15),
);

GET request (with caching)

Response response = await HttpService.get(
  apiUri: Uri.parse('https://api.example.com/posts'),
  ttl: const Duration(hours: 1),
);

// response.data is already decoded (Map / List / String)
print(response.data);

POST request

Response response = await HttpService.post(
  apiUri: Uri.parse('https://api.example.com/posts'),
  body: {'title': 'Hello', 'userId': 1},
  headers: {'Authorization': 'Bearer <token>'},
);

File upload (multipart)

Response response = await HttpService.upload(
  apiUri: Uri.parse('https://api.example.com/upload'),
  filePath: '/path/to/file.pdf',
  fieldName: 'file',
  additionalFields: {'category': 'documents'},
);

Cache utilities

// View cache statistics
Map<String, int> stats = await HttpService.getCacheStats();

// Remove only expired entries
await HttpService.clearExpiredCache();

// Wipe the entire cache
await HttpService.deleteAllCacheData();

SSL Certificate Pinning

Enable SSL pinning to protect against man-in-the-middle attacks. The library supports two pinning methods:

Method When to Use
Public Key Hash Pinning When publicKeyHashes is provided — validates SHA-256 hash of server's public key
Certificate Pinning When trustedCertificates is provided — validates against exact certificate

Note: If publicKeyHashes is provided, public key hash pinning takes priority. The library automatically selects the appropriate validation method based on your configuration.

Pin the SHA-256 hash of your server's public key. This approach is preferred because certificate renewals don't require app updates as long as the same key pair is reused.

HttpService.configureSslPinning(
  const SslPinningConfig(
    enabled: true,
    publicKeyHashes: [
      // Primary key hash (current certificate)
      'sha256/AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=',
      // Backup key hash (for seamless certificate rotation)
      'sha256/BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB=',
    ],
    allowedHosts: ['api.example.com'], // Optional: pin specific hosts only
  ),
);

To get your server's public key hash:

openssl s_client -connect your-server.com:443 -servername your-server.com 2>/dev/null | \
  openssl x509 -pubkey -noout | \
  openssl pkey -pubin -outform DER | \
  openssl dgst -sha256 -binary | \
  base64
Aspect Public Key Hash Pinning Certificate Pinning
Certificate Renewal ✅ No app update needed ❌ Requires app update
Maintenance Low High
Security Strong Strong

Option 2: Full Certificate Pinning

Store your certificates in your consuming project (e.g., assets/certificates/) and configure pinning at app startup:

import 'package:flutter/services.dart';
import 'package:igot_http_service_helper/igot_http_service.dart';

Future<void> initializeHttpService({bool enableSslPinning = true}) async {
  // Basic configuration
  HttpService.configure(
    connectTimeout: const Duration(seconds: 10),
    receiveTimeout: const Duration(seconds: 30),
  );

  // SSL Pinning (certificates managed in your project)
  if (enableSslPinning) {
    // Load certificate from your app's assets
    final certData = await rootBundle.load('assets/certificates/api_cert.pem');
    
    HttpService.configureSslPinning(
      SslPinningConfig(
        enabled: true,
        trustedCertificates: [certData.buffer.asUint8List()],
        allowedHosts: ['api.example.com'], // Optional: pin specific hosts only
      ),
    );
  }
}

Multiple certificates:

final cert1 = await rootBundle.load('assets/certificates/api_cert.pem');
final cert2 = await rootBundle.load('assets/certificates/backup_cert.pem');

HttpService.configureSslPinning(
  SslPinningConfig(
    enabled: true,
    trustedCertificates: [
      cert1.buffer.asUint8List(),
      cert2.buffer.asUint8List(),
    ],
  ),
);

Disable pinning at runtime:

HttpService.disableSslPinning();

Note: For certificate pinning, ensure your consuming project's pubspec.yaml includes the certificates in assets:

flutter:
  assets:
    - assets/certificates/

Response Handling

All methods return dio.Response<dynamic>. Access the body via response.data:

Response response = await HttpService.get(apiUri: Uri.parse('...'));

// If the server returns JSON, Dio decodes it automatically:
final data = response.data as Map<String, dynamic>;

// Check the HTTP status code:
if (response.statusCode == 200) { ... }

On network / HTTP errors, HttpService catches DioException internally and returns a structured error response rather than throwing, so callers can check the status code without a try/catch.


Configuration Details

Tool Version
Flutter 3.35.7 (channel stable)
Dart 3.9.2
Dio ^5.9.1
Hive Flutter ^1.1.0
DevTools 2.48.0