|
1 | | -# ht_shared |
| 1 | +# 🛠️ ht_shared |
2 | 2 |
|
3 | 3 |  |
4 | 4 | [](https://pub.dev/packages/very_good_analysis) |
5 | 5 | [](https://polyformproject.org/licenses/free-trial/1.0.0) |
6 | 6 |
|
7 | | -A shared Dart package containing core data models for news-related entities (like headlines, sources, categories, countries), pagination, standardized API response structures, **user content preferences**, and **application configuration**, used across the application ecosystem (Mobile App, Backend API, Web Dashboard). |
8 | | - |
9 | | -## Getting Started |
10 | | - |
11 | | -To use this package, add `ht_shared` as a dependency in your `pubspec.yaml` file. |
12 | | - |
13 | | -```yaml |
14 | | -dependencies: |
15 | | - ht_shared: |
16 | | - git: |
17 | | - url: https://github.com/headlines-toolkit/ht-shared.git |
18 | | -``` |
19 | | -
|
20 | | -Then, run `flutter pub get` or `dart pub get`. |
21 | | - |
22 | | -## Features |
23 | | - |
24 | | -This package provides the following core data models: |
25 | | - |
26 | | -* **`Headline`**: Represents a news headline article, including ID, title, description, URLs, publication date, and optional associated `Source` and `Category`. |
27 | | -* **`Category`**: Represents a news category with an ID, name, and optional description and icon URL. |
28 | | -* **`Source`**: Represents a news source, including ID, name, description, URL, language, optional headquarters (`Country`), and a `SourceType` enum (e.g., `newsAgency`, `blog`). |
29 | | -* **`Country`**: Represents a country with an ID, ISO code, name, and flag URL. |
30 | | -* **`UserContentPreferences`**: Represents a collection of user-specific content preferences, including followed countries, sources, categories, and saved headlines. This model stores full objects for these items and is subject to tiered limits based on user role. |
31 | | -* **`AppConfig`**: Represents the overall application configuration. This model serves as a central container for various configuration settings, including user preference limits, and is designed to be fetched and managed via the `HtDataClient`. |
32 | | -* **`UserPreferenceLimits`**: Defines the maximum number of items a user can follow or save, tiered by user role (Guest, Authenticated, Premium). This model is part of the `AppConfig` and is used for backend enforcement and client-side UI/UX. |
33 | | -* **`UserAppSettings`**: Represents a collection of user-specific application settings, unifying display preferences (`DisplaySettings`) and language selection (`AppLanguage`). This model is designed for management via a generic data client (`HtDataClient`). |
34 | | -* **`User`**: Represents a user within the system, including their assigned `role`. |
35 | | -* **`PaginatedResponse<T>`**: A generic class for handling paginated API responses, containing a list of items (`items`), a `cursor` for the next page, and a `hasMore` flag. |
36 | | -* **`AuthSuccessResponse`**: Represents the successful result of an authentication operation, typically containing the authenticated user details and an access token. |
37 | | -* **`SuccessApiResponse<T>`**: A generic wrapper for successful API responses, containing the main `data` payload (of type `T`) and optional `ResponseMetadata`. |
38 | | -* **`ResponseMetadata`**: Contains optional metadata for API responses, such as a `requestId` and `timestamp`. |
39 | | -* **`HtHttpException` Hierarchy**: A standardized set of exception classes (`NetworkException`, `BadRequestException`, `AuthenticationException`, `InvalidInputException`, `NotFoundException`, `OperationFailedException`, `ConflictException`, etc.) intended to be used by data client implementations to provide a consistent error contract. See the documentation within `ht_http_exception.dart` and individual exception files for detailed usage patterns. |
40 | | - |
41 | | -## Usage |
42 | | - |
43 | | -Import the models barrel file (`package:ht_shared/ht_shared.dart`) and use the classes as needed. |
44 | | - |
45 | | -```dart |
46 | | -import 'package:ht_shared/ht_shared.dart'; |
47 | | -
|
48 | | -void main() { |
49 | | - // Example: Creating a Source and a Headline |
50 | | - final source = Source( |
51 | | - id: 'tech-crunch', |
52 | | - name: 'TechCrunch', |
53 | | - type: SourceType.specializedPublisher, |
54 | | - url: 'https://techcrunch.com/', |
55 | | - ); |
56 | | -
|
57 | | - final headline = Headline( |
58 | | - id: 'headline-1', // Added ID for clarity in preferences example |
59 | | - title: 'New Gadget Announced', |
60 | | - description: 'A revolutionary new device changes everything.', |
61 | | - url: 'https://techcrunch.com/news/new-gadget', |
62 | | - publishedAt: DateTime.now().subtract(const Duration(hours: 1)), |
63 | | - source: source, |
64 | | - category: Category(id: 'tech', name: 'Technology'), |
65 | | - ); |
66 | | -
|
67 | | - print('Headline: ${headline.title} from ${headline.source?.name}'); |
68 | | -
|
69 | | - // Example: Creating User Content Preferences |
70 | | - final userPreferences = UserContentPreferences( |
71 | | - id: 'user-abc', |
72 | | - followedCountries: [ |
73 | | - Country(id: 'us', isoCode: 'US', name: 'United States', flagUrl: '...'), |
74 | | - Country(id: 'gb', isoCode: 'GB', name: 'United Kingdom', flagUrl: '...'), |
75 | | - ], |
76 | | - followedSources: [ |
77 | | - source, // Using the source created above |
78 | | - Source(id: 'bbc', name: 'BBC News', type: SourceType.nationalNewsOutlet), |
79 | | - ], |
80 | | - followedCategories: [ |
81 | | - Category(id: 'sports', name: 'Sports'), |
82 | | - Category(id: 'business', name: 'Business'), |
83 | | - ], |
84 | | - savedHeadlines: [ |
85 | | - headline, // Saving the headline created above |
86 | | - Headline(id: 'headline-2', title: 'Another Saved Article'), |
87 | | - ], |
88 | | - ); |
89 | | -
|
90 | | - print('\nUser ${userPreferences.id} follows ${userPreferences.followedSources.length} sources.'); |
91 | | - print('User ${userPreferences.id} has ${userPreferences.savedHeadlines.length} saved headlines.'); |
92 | | -
|
93 | | - // Example: Accessing Application Configuration and User Preference Limits |
94 | | - const appConfig = AppConfig( |
95 | | - id: 'app_config', |
96 | | - userPreferenceLimits: UserPreferenceLimits( |
97 | | - guestFollowedItemsLimit: 5, |
98 | | - guestSavedHeadlinesLimit: 10, |
99 | | - authenticatedFollowedItemsLimit: 15, |
100 | | - authenticatedSavedHeadlinesLimit: 30, |
101 | | - premiumFollowedItemsLimit: 30, |
102 | | - premiumSavedHeadlinesLimit: 100, |
103 | | - ), |
104 | | - ); |
105 | | -
|
106 | | - print('\nApp Config ID: ${appConfig.id}'); |
107 | | - print('Premium user saved headlines limit: ${appConfig.userPreferenceLimits.premiumSavedHeadlinesLimit}'); |
108 | | -
|
109 | | - // Example: Representing a paginated response of Headlines |
110 | | -
|
111 | | - // Example: Representing a paginated response of Headlines |
112 | | - final response = PaginatedResponse<Headline>( |
113 | | - items: [headline], |
114 | | - cursor: 'nextPageToken123', |
115 | | - hasMore: true, |
116 | | - ); |
117 | | -
|
118 | | - print('Fetched ${response.items.length} headlines. More available: ${response.hasMore}'); |
119 | | -
|
120 | | - // Example: Wrapping a response in SuccessApiResponse |
121 | | - final apiResponse = SuccessApiResponse<PaginatedResponse<Headline>>( |
122 | | - data: response, |
123 | | - metadata: ResponseMetadata( |
124 | | - requestId: 'req-abc-123', |
125 | | - timestamp: DateTime.now(), |
126 | | - ), |
127 | | - ); |
128 | | -
|
129 | | - print('API Response Request ID: ${apiResponse.metadata?.requestId}'); |
130 | | - print('API Response Data Type: ${apiResponse.data.runtimeType}'); |
131 | | -
|
132 | | - // Example: Catching a shared exception |
133 | | - try { |
134 | | - // Simulate an operation that might throw |
135 | | - throw NotFoundException("Item '123' could not be located."); |
136 | | - } on HtHttpException catch (e) { |
137 | | - // Handle any standard HT exception |
138 | | - print('Caught standard exception: $e'); |
139 | | - } catch (e) { |
140 | | - // Handle other unexpected errors |
141 | | - print('Caught unexpected error: $e'); |
142 | | - } |
143 | | -} |
144 | | -
|
145 | | -``` |
146 | | - |
147 | | -## License |
148 | | - |
149 | | -This package is licensed under the [PolyForm Free Trial](LICENSE). Please review the terms before use. |
| 7 | +The essential shared Dart package providing the **Core Data Models** for the **Headlines Toolkit**. `ht_shared` ensures data consistency and accelerates development across our Flutter mobile app, web dashboard, and Dart Frog backend API. |
| 8 | + |
| 9 | +Think of it as the common language 🗣️ that all parts of your news application will speak! |
| 10 | + |
| 11 | +## ✨ Why `ht_shared` Matters |
| 12 | + |
| 13 | +* **🧱 Unified Data Structure:** Guarantees that your `Headline`, `Source`, `User`, `FeedItem`, and configuration data are handled identically across the entire Headlines Toolkit. |
| 14 | +* **🚀 Rapid Development:** Start building features faster with pre-defined, robust models for common news application needs. No reinventing the wheel! |
| 15 | +* **🔗 Seamless Integration:** Enables the Flutter mobile app, web dashboard, and Dart Frog API to work together flawlessly. |
| 16 | +* **🎯 Consistency by Design:** Reduces errors and simplifies maintenance by providing a single source of truth for core data definitions. |
| 17 | +* **🌟 Foundation for Rich Features:** Includes models for user personalization (preferences, settings), dynamic feeds, and standardized API responses. |
| 18 | + |
| 19 | +## 🎁 Key Models Provided |
| 20 | + |
| 21 | +This package includes well-defined Dart classes for: |
| 22 | + |
| 23 | +* 📰 **News Content:** `Headline`, `Category`, `Source`, `Country` |
| 24 | +* 🧩 **Feed System:** `FeedItem` (and its subtypes like `Ad`, `SuggestedContent`, `EngagementContent`), `FeedItemAction` |
| 25 | +* 👤 **User Data:** `User`, `UserContentPreferences`, `UserPreferenceLimits`, `UserAppSettings` |
| 26 | +* ⚙️ **Application Configuration:** `AppConfig` |
| 27 | +* 📡 **API Communication:** `PaginatedResponse`, `SuccessApiResponse`, and a comprehensive `HtHttpException` hierarchy for standardized error handling. |
| 28 | + |
| 29 | +## 🔑 Access and Licensing |
| 30 | + |
| 31 | +`ht_shared` is source-available as part of the Headlines Toolkit ecosystem. |
| 32 | + |
| 33 | +The source code for `ht_shared` is available for review as part of the Headlines |
| 34 | +Toolkit ecosystem. To acquire a commercial license for building unlimited news |
| 35 | +applications with the Headlines Toolkit repositories, please visit the |
| 36 | +[Headlines Toolkit GitHub organization page](https://github.com/headlines-toolkit) |
| 37 | +for more details. |
| 38 | + |
| 39 | +## 🚀 Getting Started |
| 40 | + |
| 41 | +To integrate `ht_shared` into a Headlines Toolkit component (or your custom Dart/Flutter project): |
| 42 | + |
| 43 | +1. Add `ht_shared` as a dependency in your `pubspec.yaml` file: |
| 44 | + |
| 45 | + ```yaml |
| 46 | + dependencies: |
| 47 | + ht_shared: |
| 48 | + git: |
| 49 | + url: https://github.com/headlines-toolkit/ht-shared.git |
| 50 | + # You might want to pin to a specific ref/tag in a real project: |
| 51 | + # ref: main |
| 52 | + ``` |
| 53 | + |
| 54 | +2. Run `dart pub get` (or `flutter pub get` for Flutter projects). |
| 55 | + |
| 56 | +3. Import `package:ht_shared/ht_shared.dart` to access all shared models and utilities. |
| 57 | + |
| 58 | + ```dart |
| 59 | + import 'package:ht_shared/ht_shared.dart'; |
| 60 | + ``` |
0 commit comments