@zssz-soft/firebase-functions-shared 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +391 -0
- package/lib/config/app.config.d.ts +106 -0
- package/lib/config/app.config.d.ts.map +1 -0
- package/lib/config/app.config.js +55 -0
- package/lib/config/app.config.js.map +1 -0
- package/lib/config/index.d.ts +2 -0
- package/lib/config/index.d.ts.map +1 -0
- package/lib/config/index.js +18 -0
- package/lib/config/index.js.map +1 -0
- package/lib/index.d.ts +13 -0
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +29 -0
- package/lib/index.js.map +1 -0
- package/lib/modules/bootstrap/bootstrap.d.ts +4 -0
- package/lib/modules/bootstrap/bootstrap.d.ts.map +1 -0
- package/lib/modules/bootstrap/bootstrap.js +162 -0
- package/lib/modules/bootstrap/bootstrap.js.map +1 -0
- package/lib/modules/bootstrap/bootstrap.models.d.ts +20 -0
- package/lib/modules/bootstrap/bootstrap.models.d.ts.map +1 -0
- package/lib/modules/bootstrap/bootstrap.models.js +3 -0
- package/lib/modules/bootstrap/bootstrap.models.js.map +1 -0
- package/lib/modules/bootstrap/index.d.ts +3 -0
- package/lib/modules/bootstrap/index.d.ts.map +1 -0
- package/lib/modules/bootstrap/index.js +19 -0
- package/lib/modules/bootstrap/index.js.map +1 -0
- package/lib/modules/email/email.d.ts +5 -0
- package/lib/modules/email/email.d.ts.map +1 -0
- package/lib/modules/email/email.js +105 -0
- package/lib/modules/email/email.js.map +1 -0
- package/lib/modules/email/email.models.d.ts +25 -0
- package/lib/modules/email/email.models.d.ts.map +1 -0
- package/lib/modules/email/email.models.js +3 -0
- package/lib/modules/email/email.models.js.map +1 -0
- package/lib/modules/email/email.service.d.ts +11 -0
- package/lib/modules/email/email.service.d.ts.map +1 -0
- package/lib/modules/email/email.service.js +227 -0
- package/lib/modules/email/email.service.js.map +1 -0
- package/lib/modules/email/email.validator.d.ts +2 -0
- package/lib/modules/email/email.validator.d.ts.map +1 -0
- package/lib/modules/email/email.validator.js +9 -0
- package/lib/modules/email/email.validator.js.map +1 -0
- package/lib/modules/email/index.d.ts +5 -0
- package/lib/modules/email/index.d.ts.map +1 -0
- package/lib/modules/email/index.js +21 -0
- package/lib/modules/email/index.js.map +1 -0
- package/lib/modules/security/effective-permissions.d.ts +28 -0
- package/lib/modules/security/effective-permissions.d.ts.map +1 -0
- package/lib/modules/security/effective-permissions.js +133 -0
- package/lib/modules/security/effective-permissions.js.map +1 -0
- package/lib/modules/security/effective-permissions.models.d.ts +96 -0
- package/lib/modules/security/effective-permissions.models.d.ts.map +1 -0
- package/lib/modules/security/effective-permissions.models.js +24 -0
- package/lib/modules/security/effective-permissions.models.js.map +1 -0
- package/lib/modules/security/effective-permissions.triggers.d.ts +83 -0
- package/lib/modules/security/effective-permissions.triggers.d.ts.map +1 -0
- package/lib/modules/security/effective-permissions.triggers.js +307 -0
- package/lib/modules/security/effective-permissions.triggers.js.map +1 -0
- package/lib/modules/security/index.d.ts +10 -0
- package/lib/modules/security/index.d.ts.map +1 -0
- package/lib/modules/security/index.js +28 -0
- package/lib/modules/security/index.js.map +1 -0
- package/lib/modules/storage/index.d.ts +2 -0
- package/lib/modules/storage/index.d.ts.map +1 -0
- package/lib/modules/storage/index.js +18 -0
- package/lib/modules/storage/index.js.map +1 -0
- package/lib/modules/storage/thumbnail-functions.d.ts +10 -0
- package/lib/modules/storage/thumbnail-functions.d.ts.map +1 -0
- package/lib/modules/storage/thumbnail-functions.js +482 -0
- package/lib/modules/storage/thumbnail-functions.js.map +1 -0
- package/lib/modules/user/index.d.ts +4 -0
- package/lib/modules/user/index.d.ts.map +1 -0
- package/lib/modules/user/index.js +20 -0
- package/lib/modules/user/index.js.map +1 -0
- package/lib/modules/user/user-management.d.ts +29 -0
- package/lib/modules/user/user-management.d.ts.map +1 -0
- package/lib/modules/user/user-management.js +134 -0
- package/lib/modules/user/user-management.js.map +1 -0
- package/lib/modules/user/user.d.ts +2 -0
- package/lib/modules/user/user.d.ts.map +1 -0
- package/lib/modules/user/user.js +15 -0
- package/lib/modules/user/user.js.map +1 -0
- package/lib/modules/user/user.models.d.ts +15 -0
- package/lib/modules/user/user.models.d.ts.map +1 -0
- package/lib/modules/user/user.models.js +6 -0
- package/lib/modules/user/user.models.js.map +1 -0
- package/package.json +72 -0
package/README.md
ADDED
|
@@ -0,0 +1,391 @@
|
|
|
1
|
+
# LodgeFlow Shared Firebase Functions
|
|
2
|
+
|
|
3
|
+
A shared library of Firebase Cloud Functions modules for LodgeFlow applications. This library provides common functionality for user management, email services, file storage, and system bootstrap across multiple Firebase projects.
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
- **Bootstrap Module**: System initialization with default admin user and roles
|
|
8
|
+
- **Email Module**: Templated email service (welcome, password reset, notifications)
|
|
9
|
+
- **Storage Module**: Image/document processing with thumbnail generation and HEIC conversion
|
|
10
|
+
- **User Module**: User management with Firebase Auth and Firestore integration
|
|
11
|
+
- **Configuration Management**: Centralized configuration for multi-tenant deployments
|
|
12
|
+
|
|
13
|
+
## Installation
|
|
14
|
+
|
|
15
|
+
```bash
|
|
16
|
+
cd firebase/shared/functions
|
|
17
|
+
npm install
|
|
18
|
+
npm run build
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
## Usage
|
|
22
|
+
|
|
23
|
+
### 1. Initialize Configuration
|
|
24
|
+
|
|
25
|
+
Before using any shared functions, you must initialize the application configuration in your main `index.ts` file:
|
|
26
|
+
|
|
27
|
+
```typescript
|
|
28
|
+
import { initializeApp } from 'firebase-admin/app';
|
|
29
|
+
import { setGlobalOptions } from 'firebase-functions/v2';
|
|
30
|
+
import { initializeConfig, AppConfig } from '@lodgeflow/firebase-functions-shared';
|
|
31
|
+
|
|
32
|
+
// Initialize Firebase Admin SDK
|
|
33
|
+
initializeApp({
|
|
34
|
+
projectId: process.env.GCLOUD_PROJECT || 'your-project-id',
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
// Configure shared library
|
|
38
|
+
const config: AppConfig = {
|
|
39
|
+
projectId: process.env.GCLOUD_PROJECT || 'your-project-id',
|
|
40
|
+
region: process.env.FUNCTION_REGION || 'europe-west1',
|
|
41
|
+
firestoreDatabaseId: process.env.FIRESTORE_DATABASE_ID, // Optional
|
|
42
|
+
appName: 'Your App Name',
|
|
43
|
+
defaultAdminPassword: process.env.DEFAULT_ADMIN_PASSWORD || 'AdminBootstrap2024!',
|
|
44
|
+
defaultUserPassword: process.env.DEFAULT_USER_PASSWORD || 'User2024!',
|
|
45
|
+
defaultAdminRoleId: '66000',
|
|
46
|
+
defaultUserRoleId: '66001',
|
|
47
|
+
defaultLoginUrl: process.env.DEFAULT_LOGIN_URL || 'https://yourapp.web.app/login',
|
|
48
|
+
maxInstances: 10,
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
initializeConfig(config);
|
|
52
|
+
|
|
53
|
+
// Set global function options
|
|
54
|
+
setGlobalOptions({
|
|
55
|
+
maxInstances: config.maxInstances,
|
|
56
|
+
region: config.region,
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
// Export functions
|
|
60
|
+
export * from '@lodgeflow/firebase-functions-shared';
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
### 2. Environment Variables
|
|
64
|
+
|
|
65
|
+
Create a `.env` file in your functions directory:
|
|
66
|
+
|
|
67
|
+
```bash
|
|
68
|
+
# Firebase Configuration
|
|
69
|
+
GCLOUD_PROJECT=your-project-id
|
|
70
|
+
FUNCTION_REGION=europe-west1
|
|
71
|
+
FIRESTORE_DATABASE_ID=default # Optional
|
|
72
|
+
|
|
73
|
+
# Email Configuration (SMTP)
|
|
74
|
+
EMAIL_HOST=smtp.gmail.com
|
|
75
|
+
EMAIL_PORT=587
|
|
76
|
+
EMAIL_SECURE=false
|
|
77
|
+
EMAIL_USER=your-email@gmail.com
|
|
78
|
+
EMAIL_PASS=your-app-password
|
|
79
|
+
EMAIL_FROM_NAME=Your App Name
|
|
80
|
+
EMAIL_FROM_EMAIL=noreply@yourapp.com
|
|
81
|
+
|
|
82
|
+
# Application Configuration
|
|
83
|
+
DEFAULT_ADMIN_PASSWORD=AdminBootstrap2024!
|
|
84
|
+
DEFAULT_USER_PASSWORD=User2024!
|
|
85
|
+
DEFAULT_LOGIN_URL=https://yourapp.web.app/login
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
### 3. Using Shared Modules
|
|
89
|
+
|
|
90
|
+
#### Bootstrap Module
|
|
91
|
+
|
|
92
|
+
Initialize your system with default admin user and roles:
|
|
93
|
+
|
|
94
|
+
```typescript
|
|
95
|
+
// Client-side usage
|
|
96
|
+
import { getFunctions, httpsCallable } from 'firebase/functions';
|
|
97
|
+
|
|
98
|
+
const functions = getFunctions();
|
|
99
|
+
const systemBootstrap = httpsCallable(functions, 'systemBootstrap');
|
|
100
|
+
|
|
101
|
+
const result = await systemBootstrap({
|
|
102
|
+
adminEmail: 'admin@yourapp.com',
|
|
103
|
+
adminDisplayName: 'Admin User',
|
|
104
|
+
adminPassword: 'SecurePassword123!',
|
|
105
|
+
});
|
|
106
|
+
|
|
107
|
+
console.log(result.data.message);
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
Check bootstrap status:
|
|
111
|
+
|
|
112
|
+
```typescript
|
|
113
|
+
const checkStatus = httpsCallable(functions, 'checkBootstrapStatus');
|
|
114
|
+
const status = await checkStatus();
|
|
115
|
+
console.log(status.data); // { isBootstrapped: true, userCount: 1 }
|
|
116
|
+
```
|
|
117
|
+
|
|
118
|
+
#### Email Module
|
|
119
|
+
|
|
120
|
+
Send templated emails:
|
|
121
|
+
|
|
122
|
+
```typescript
|
|
123
|
+
const sendEmail = httpsCallable(functions, 'sendEmail');
|
|
124
|
+
|
|
125
|
+
// Welcome email
|
|
126
|
+
await sendEmail({
|
|
127
|
+
to: 'user@example.com',
|
|
128
|
+
subject: 'Welcome!',
|
|
129
|
+
type: 'welcome',
|
|
130
|
+
userName: 'John Doe',
|
|
131
|
+
loginLink: 'https://yourapp.web.app/login',
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
// Password reset email
|
|
135
|
+
await sendEmail({
|
|
136
|
+
to: 'user@example.com',
|
|
137
|
+
subject: 'Reset Password',
|
|
138
|
+
type: 'password-reset',
|
|
139
|
+
userName: 'John Doe',
|
|
140
|
+
resetLink: 'https://yourapp.web.app/reset?token=abc123',
|
|
141
|
+
});
|
|
142
|
+
|
|
143
|
+
// Notification email
|
|
144
|
+
await sendEmail({
|
|
145
|
+
to: 'user@example.com',
|
|
146
|
+
subject: 'Important Update',
|
|
147
|
+
type: 'notification',
|
|
148
|
+
message: 'Your account has been updated.',
|
|
149
|
+
});
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
#### Storage Module
|
|
153
|
+
|
|
154
|
+
Generate thumbnails for images and documents:
|
|
155
|
+
|
|
156
|
+
```typescript
|
|
157
|
+
const generateThumbnail = httpsCallable(functions, 'generateThumbnail');
|
|
158
|
+
|
|
159
|
+
const result = await generateThumbnail({
|
|
160
|
+
path: 'gs://your-bucket/path/to/image.jpg',
|
|
161
|
+
maxWidth: 512,
|
|
162
|
+
maxHeight: 512,
|
|
163
|
+
force: false, // Set to true to regenerate existing thumbnails
|
|
164
|
+
documentId: 'optional-document-id', // Updates Firestore document with thumbnail URL
|
|
165
|
+
});
|
|
166
|
+
|
|
167
|
+
console.log(result.data);
|
|
168
|
+
// {
|
|
169
|
+
// success: true,
|
|
170
|
+
// path: 'path/to/image.jpg',
|
|
171
|
+
// thumbPath: 'https://.../_thumb.webp',
|
|
172
|
+
// webImagePath: 'https://.../_web.jpg', // For HEIC files only
|
|
173
|
+
// created: true
|
|
174
|
+
// }
|
|
175
|
+
```
|
|
176
|
+
|
|
177
|
+
#### User Module
|
|
178
|
+
|
|
179
|
+
Create users with automatic email notification:
|
|
180
|
+
|
|
181
|
+
```typescript
|
|
182
|
+
const createUser = httpsCallable(functions, 'createUserWithEmail');
|
|
183
|
+
|
|
184
|
+
const result = await createUser({
|
|
185
|
+
email: 'newuser@example.com',
|
|
186
|
+
firstName: 'John',
|
|
187
|
+
lastName: 'Doe',
|
|
188
|
+
password: 'SecurePassword123!',
|
|
189
|
+
phoneNumber: '+1234567890',
|
|
190
|
+
roleIds: ['66001'], // USER role
|
|
191
|
+
sendWelcomeEmail: true,
|
|
192
|
+
loginUrl: 'https://yourapp.web.app/login',
|
|
193
|
+
});
|
|
194
|
+
|
|
195
|
+
console.log(result.data);
|
|
196
|
+
// { success: true, uid: '...', email: '...', emailSent: true }
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
## Module Details
|
|
200
|
+
|
|
201
|
+
### Bootstrap Module
|
|
202
|
+
|
|
203
|
+
**Functions:**
|
|
204
|
+
|
|
205
|
+
- `systemBootstrap(data)` - Creates initial admin user and default roles
|
|
206
|
+
- `checkBootstrapStatus()` - Checks if system has been initialized
|
|
207
|
+
|
|
208
|
+
**Default Roles:**
|
|
209
|
+
|
|
210
|
+
- **ADMIN** (ID: 66000): Full administrative access
|
|
211
|
+
- **USER** (ID: 66001): Standard user access
|
|
212
|
+
|
|
213
|
+
### Email Module
|
|
214
|
+
|
|
215
|
+
**Supported Email Types:**
|
|
216
|
+
|
|
217
|
+
- `welcome` - Welcome email with login link
|
|
218
|
+
- `password-reset` - Password reset email with reset link
|
|
219
|
+
- `notification` - Generic notification email
|
|
220
|
+
- `custom` - Custom HTML email
|
|
221
|
+
|
|
222
|
+
**Configuration:**
|
|
223
|
+
All emails use the application name from the configuration and support both HTML and plain text formats.
|
|
224
|
+
|
|
225
|
+
### Storage Module
|
|
226
|
+
|
|
227
|
+
**Supported File Types:**
|
|
228
|
+
|
|
229
|
+
- **Images**: jpg, jpeg, png, webp, avif, gif, bmp, tiff, heic, heif
|
|
230
|
+
- **Documents**: pdf, doc, docx, xls, xlsx, ppt, pptx, txt, rtf, odt, ods, odp
|
|
231
|
+
|
|
232
|
+
**Features:**
|
|
233
|
+
|
|
234
|
+
- Automatic HEIC to JPEG conversion (web-optimized)
|
|
235
|
+
- WebP thumbnail generation (512x512 default)
|
|
236
|
+
- Empty placeholder thumbnails for non-image files
|
|
237
|
+
- Automatic Firestore document updates with thumbnail URLs
|
|
238
|
+
- Efficient caching (1 year max-age)
|
|
239
|
+
|
|
240
|
+
### User Module
|
|
241
|
+
|
|
242
|
+
**Features:**
|
|
243
|
+
|
|
244
|
+
- Creates users in both Firebase Auth and Firestore
|
|
245
|
+
- Automatic welcome email sending
|
|
246
|
+
- Default role assignment (USER role)
|
|
247
|
+
- Transaction-safe with automatic cleanup on errors
|
|
248
|
+
- Supports custom passwords or generates secure defaults
|
|
249
|
+
|
|
250
|
+
## Configuration Reference
|
|
251
|
+
|
|
252
|
+
### AppConfig Interface
|
|
253
|
+
|
|
254
|
+
```typescript
|
|
255
|
+
interface AppConfig {
|
|
256
|
+
projectId: string; // Firebase project ID
|
|
257
|
+
region: string; // Cloud Functions region
|
|
258
|
+
firestoreDatabaseId?: string; // Optional Firestore database ID
|
|
259
|
+
appName: string; // Application name for branding
|
|
260
|
+
defaultAdminPassword: string; // Bootstrap admin password
|
|
261
|
+
defaultUserPassword: string; // Default password for new users
|
|
262
|
+
defaultAdminRoleId: string; // Admin role ID in Firestore
|
|
263
|
+
defaultUserRoleId: string; // User role ID in Firestore
|
|
264
|
+
defaultLoginUrl: string; // Default login URL for emails
|
|
265
|
+
maxInstances?: number; // Max Cloud Function instances
|
|
266
|
+
}
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
### EmailConfig Interface
|
|
270
|
+
|
|
271
|
+
```typescript
|
|
272
|
+
interface EmailConfig {
|
|
273
|
+
host: string; // SMTP server hostname
|
|
274
|
+
port: number; // SMTP port (587 or 465)
|
|
275
|
+
secure: boolean; // TLS/SSL enabled
|
|
276
|
+
user: string; // SMTP username
|
|
277
|
+
pass: string; // SMTP password
|
|
278
|
+
fromName: string; // Sender display name
|
|
279
|
+
fromEmail: string; // Sender email address
|
|
280
|
+
}
|
|
281
|
+
```
|
|
282
|
+
|
|
283
|
+
## Security Best Practices
|
|
284
|
+
|
|
285
|
+
1. **Environment Variables**: Store sensitive data in environment variables, not in code
|
|
286
|
+
2. **Firebase Secrets**: Use Firebase Secrets Manager for production:
|
|
287
|
+
```bash
|
|
288
|
+
firebase functions:secrets:set EMAIL_PASS
|
|
289
|
+
```
|
|
290
|
+
3. **Authentication**: All functions require authentication except bootstrap status check
|
|
291
|
+
4. **Role-Based Access**: Implement proper role checks in your application
|
|
292
|
+
5. **Password Policies**: Enforce strong passwords (min 6 characters)
|
|
293
|
+
6. **Email Verification**: Users should verify their email addresses
|
|
294
|
+
|
|
295
|
+
## Development
|
|
296
|
+
|
|
297
|
+
### Build
|
|
298
|
+
|
|
299
|
+
```bash
|
|
300
|
+
npm run build
|
|
301
|
+
```
|
|
302
|
+
|
|
303
|
+
### Watch Mode
|
|
304
|
+
|
|
305
|
+
```bash
|
|
306
|
+
npm run build:watch
|
|
307
|
+
```
|
|
308
|
+
|
|
309
|
+
### Testing
|
|
310
|
+
|
|
311
|
+
```bash
|
|
312
|
+
npm test
|
|
313
|
+
```
|
|
314
|
+
|
|
315
|
+
### Linting
|
|
316
|
+
|
|
317
|
+
```bash
|
|
318
|
+
npm run lint
|
|
319
|
+
```
|
|
320
|
+
|
|
321
|
+
## Migration Guide
|
|
322
|
+
|
|
323
|
+
### From Standalone to Shared Library
|
|
324
|
+
|
|
325
|
+
1. **Install the shared library** in your Firebase functions project
|
|
326
|
+
2. **Update your index.ts** to initialize configuration
|
|
327
|
+
3. **Remove duplicate code** from your project (bootstrap, email, storage, user modules)
|
|
328
|
+
4. **Update imports** to use the shared library
|
|
329
|
+
5. **Configure environment variables** according to the template above
|
|
330
|
+
6. **Test thoroughly** in emulator before deploying
|
|
331
|
+
|
|
332
|
+
Example migration:
|
|
333
|
+
|
|
334
|
+
```typescript
|
|
335
|
+
// Before
|
|
336
|
+
import { systemBootstrap } from './modules/bootstrap/bootstrap';
|
|
337
|
+
export { systemBootstrap };
|
|
338
|
+
|
|
339
|
+
// After
|
|
340
|
+
import { initializeConfig, AppConfig } from '@lodgeflow/firebase-functions-shared';
|
|
341
|
+
|
|
342
|
+
const config: AppConfig = {
|
|
343
|
+
/* your config */
|
|
344
|
+
};
|
|
345
|
+
initializeConfig(config);
|
|
346
|
+
|
|
347
|
+
export * from '@lodgeflow/firebase-functions-shared';
|
|
348
|
+
```
|
|
349
|
+
|
|
350
|
+
## Contributing
|
|
351
|
+
|
|
352
|
+
This is a private shared library for LodgeFlow applications. To contribute:
|
|
353
|
+
|
|
354
|
+
1. Make changes in the `firebase/shared/functions` directory
|
|
355
|
+
2. Test changes in emulator with one of the consumer projects
|
|
356
|
+
3. Update version in `package.json`
|
|
357
|
+
4. Build and deploy
|
|
358
|
+
|
|
359
|
+
## Troubleshooting
|
|
360
|
+
|
|
361
|
+
### Configuration Not Initialized Error
|
|
362
|
+
|
|
363
|
+
**Error**: `Application configuration not initialized. Call initializeConfig() first.`
|
|
364
|
+
|
|
365
|
+
**Solution**: Ensure you call `initializeConfig(config)` before exporting any functions.
|
|
366
|
+
|
|
367
|
+
### Email Sending Fails
|
|
368
|
+
|
|
369
|
+
**Error**: `Email configuration incomplete`
|
|
370
|
+
|
|
371
|
+
**Solution**: Check that all required environment variables are set (EMAIL_HOST, EMAIL_USER, EMAIL_PASS).
|
|
372
|
+
|
|
373
|
+
### Firestore Database Not Found
|
|
374
|
+
|
|
375
|
+
**Error**: `Firestore database "default" not found`
|
|
376
|
+
|
|
377
|
+
**Solution**: Either create the database in Firebase Console or set `firestoreDatabaseId` to undefined to use the default database.
|
|
378
|
+
|
|
379
|
+
### HEIC Conversion Fails
|
|
380
|
+
|
|
381
|
+
**Error**: `Failed to convert HEIC to JPEG`
|
|
382
|
+
|
|
383
|
+
**Solution**: Ensure `heic-convert` and `sharp` are installed. Check that the file is a valid HEIC image.
|
|
384
|
+
|
|
385
|
+
## License
|
|
386
|
+
|
|
387
|
+
UNLICENSED - Private library for ZS-Soft/LodgeFlow applications.
|
|
388
|
+
|
|
389
|
+
## Support
|
|
390
|
+
|
|
391
|
+
For issues or questions, contact the development team or create an issue in the project repository.
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Application Configuration
|
|
3
|
+
*
|
|
4
|
+
* Centralized configuration for Firebase Functions shared modules.
|
|
5
|
+
* Each application should provide its own configuration values.
|
|
6
|
+
*/
|
|
7
|
+
export interface AppConfig {
|
|
8
|
+
/**
|
|
9
|
+
* Firebase project ID
|
|
10
|
+
* Used for initializing Firebase Admin SDK
|
|
11
|
+
*/
|
|
12
|
+
projectId: string;
|
|
13
|
+
/**
|
|
14
|
+
* Cloud Functions deployment region
|
|
15
|
+
* Examples: 'europe-west1', 'europe-west4', 'us-central1'
|
|
16
|
+
*/
|
|
17
|
+
region: string;
|
|
18
|
+
/**
|
|
19
|
+
* Optional Firestore database ID
|
|
20
|
+
* Leave undefined to use the default database
|
|
21
|
+
*/
|
|
22
|
+
firestoreDatabaseId?: string;
|
|
23
|
+
/**
|
|
24
|
+
* Application name for branding
|
|
25
|
+
* Used in email templates and user-facing messages
|
|
26
|
+
*/
|
|
27
|
+
appName: string;
|
|
28
|
+
/**
|
|
29
|
+
* Default admin password for system bootstrap
|
|
30
|
+
* Should be changed immediately after first login
|
|
31
|
+
*/
|
|
32
|
+
defaultAdminPassword: string;
|
|
33
|
+
/**
|
|
34
|
+
* Default password for newly created users
|
|
35
|
+
* Users should change this on first login
|
|
36
|
+
*/
|
|
37
|
+
defaultUserPassword: string;
|
|
38
|
+
/**
|
|
39
|
+
* Default admin role ID in Firestore
|
|
40
|
+
*/
|
|
41
|
+
defaultAdminRoleId: string;
|
|
42
|
+
/**
|
|
43
|
+
* Default user role ID in Firestore
|
|
44
|
+
*/
|
|
45
|
+
defaultUserRoleId: string;
|
|
46
|
+
/**
|
|
47
|
+
* Default login URL for the application
|
|
48
|
+
* Used in welcome emails and password reset links
|
|
49
|
+
*/
|
|
50
|
+
defaultLoginUrl: string;
|
|
51
|
+
/**
|
|
52
|
+
* Maximum number of Cloud Function instances
|
|
53
|
+
*/
|
|
54
|
+
maxInstances?: number;
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Email Configuration
|
|
58
|
+
*/
|
|
59
|
+
export interface EmailConfig {
|
|
60
|
+
/**
|
|
61
|
+
* SMTP server hostname
|
|
62
|
+
*/
|
|
63
|
+
host: string;
|
|
64
|
+
/**
|
|
65
|
+
* SMTP server port
|
|
66
|
+
* Common values: 587 (TLS), 465 (SSL), 25 (unsecured)
|
|
67
|
+
*/
|
|
68
|
+
port: number;
|
|
69
|
+
/**
|
|
70
|
+
* Use TLS/SSL for SMTP connection
|
|
71
|
+
* Typically true for port 465, false for port 587
|
|
72
|
+
*/
|
|
73
|
+
secure: boolean;
|
|
74
|
+
/**
|
|
75
|
+
* SMTP authentication username
|
|
76
|
+
*/
|
|
77
|
+
user: string;
|
|
78
|
+
/**
|
|
79
|
+
* SMTP authentication password
|
|
80
|
+
* Should be stored in Firebase Secrets Manager
|
|
81
|
+
*/
|
|
82
|
+
pass: string;
|
|
83
|
+
/**
|
|
84
|
+
* Email sender display name
|
|
85
|
+
*/
|
|
86
|
+
fromName: string;
|
|
87
|
+
/**
|
|
88
|
+
* Email sender address
|
|
89
|
+
*/
|
|
90
|
+
fromEmail: string;
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Initialize the application configuration
|
|
94
|
+
* Must be called before using any shared modules
|
|
95
|
+
*/
|
|
96
|
+
export declare function initializeConfig(config: AppConfig): void;
|
|
97
|
+
/**
|
|
98
|
+
* Get the current application configuration
|
|
99
|
+
* Throws an error if configuration hasn't been initialized
|
|
100
|
+
*/
|
|
101
|
+
export declare function getConfig(): AppConfig;
|
|
102
|
+
/**
|
|
103
|
+
* Load email configuration from environment variables
|
|
104
|
+
*/
|
|
105
|
+
export declare function getEmailConfig(): EmailConfig;
|
|
106
|
+
//# sourceMappingURL=app.config.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"app.config.d.ts","sourceRoot":"","sources":["../../src/config/app.config.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,MAAM,WAAW,SAAS;IACxB;;;OAGG;IACH,SAAS,EAAE,MAAM,CAAC;IAElB;;;OAGG;IACH,MAAM,EAAE,MAAM,CAAC;IAEf;;;OAGG;IACH,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAE7B;;;OAGG;IACH,OAAO,EAAE,MAAM,CAAC;IAEhB;;;OAGG;IACH,oBAAoB,EAAE,MAAM,CAAC;IAE7B;;;OAGG;IACH,mBAAmB,EAAE,MAAM,CAAC;IAE5B;;OAEG;IACH,kBAAkB,EAAE,MAAM,CAAC;IAE3B;;OAEG;IACH,iBAAiB,EAAE,MAAM,CAAC;IAE1B;;;OAGG;IACH,eAAe,EAAE,MAAM,CAAC;IAExB;;OAEG;IACH,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B;;OAEG;IACH,IAAI,EAAE,MAAM,CAAC;IAEb;;;OAGG;IACH,IAAI,EAAE,MAAM,CAAC;IAEb;;;OAGG;IACH,MAAM,EAAE,OAAO,CAAC;IAEhB;;OAEG;IACH,IAAI,EAAE,MAAM,CAAC;IAEb;;;OAGG;IACH,IAAI,EAAE,MAAM,CAAC;IAEb;;OAEG;IACH,QAAQ,EAAE,MAAM,CAAC;IAEjB;;OAEG;IACH,SAAS,EAAE,MAAM,CAAC;CACnB;AAID;;;GAGG;AACH,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,SAAS,GAAG,IAAI,CAExD;AAED;;;GAGG;AACH,wBAAgB,SAAS,IAAI,SAAS,CAKrC;AAED;;GAEG;AACH,wBAAgB,cAAc,IAAI,WAAW,CA2B5C"}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Application Configuration
|
|
4
|
+
*
|
|
5
|
+
* Centralized configuration for Firebase Functions shared modules.
|
|
6
|
+
* Each application should provide its own configuration values.
|
|
7
|
+
*/
|
|
8
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
9
|
+
exports.initializeConfig = initializeConfig;
|
|
10
|
+
exports.getConfig = getConfig;
|
|
11
|
+
exports.getEmailConfig = getEmailConfig;
|
|
12
|
+
let currentConfig = null;
|
|
13
|
+
/**
|
|
14
|
+
* Initialize the application configuration
|
|
15
|
+
* Must be called before using any shared modules
|
|
16
|
+
*/
|
|
17
|
+
function initializeConfig(config) {
|
|
18
|
+
currentConfig = config;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Get the current application configuration
|
|
22
|
+
* Throws an error if configuration hasn't been initialized
|
|
23
|
+
*/
|
|
24
|
+
function getConfig() {
|
|
25
|
+
if (!currentConfig) {
|
|
26
|
+
throw new Error('Application configuration not initialized. Call initializeConfig() first.');
|
|
27
|
+
}
|
|
28
|
+
return currentConfig;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Load email configuration from environment variables
|
|
32
|
+
*/
|
|
33
|
+
function getEmailConfig() {
|
|
34
|
+
const host = process.env.EMAIL_HOST;
|
|
35
|
+
const user = process.env.EMAIL_USER;
|
|
36
|
+
const pass = process.env.EMAIL_PASS;
|
|
37
|
+
if (!host || !user || !pass) {
|
|
38
|
+
throw new Error('Email configuration incomplete. Required environment variables: EMAIL_HOST, EMAIL_USER, EMAIL_PASS');
|
|
39
|
+
}
|
|
40
|
+
const port = parseInt(process.env.EMAIL_PORT || '587', 10);
|
|
41
|
+
const secure = process.env.EMAIL_SECURE ? process.env.EMAIL_SECURE === 'true' : port === 465;
|
|
42
|
+
const config = getConfig();
|
|
43
|
+
const fromName = process.env.EMAIL_FROM_NAME || config.appName;
|
|
44
|
+
const fromEmail = process.env.EMAIL_FROM_EMAIL || process.env.EMAIL_FROM_ADDRESS || user;
|
|
45
|
+
return {
|
|
46
|
+
host,
|
|
47
|
+
port,
|
|
48
|
+
secure,
|
|
49
|
+
user,
|
|
50
|
+
pass,
|
|
51
|
+
fromName,
|
|
52
|
+
fromEmail,
|
|
53
|
+
};
|
|
54
|
+
}
|
|
55
|
+
//# sourceMappingURL=app.config.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"app.config.js","sourceRoot":"","sources":["../../src/config/app.config.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;AA8GH,4CAEC;AAMD,8BAKC;AAKD,wCA2BC;AAnDD,IAAI,aAAa,GAAqB,IAAI,CAAC;AAE3C;;;GAGG;AACH,SAAgB,gBAAgB,CAAC,MAAiB;IAChD,aAAa,GAAG,MAAM,CAAC;AACzB,CAAC;AAED;;;GAGG;AACH,SAAgB,SAAS;IACvB,IAAI,CAAC,aAAa,EAAE,CAAC;QACnB,MAAM,IAAI,KAAK,CAAC,2EAA2E,CAAC,CAAC;IAC/F,CAAC;IACD,OAAO,aAAa,CAAC;AACvB,CAAC;AAED;;GAEG;AACH,SAAgB,cAAc;IAC5B,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC;IACpC,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC;IACpC,MAAM,IAAI,GAAG,OAAO,CAAC,GAAG,CAAC,UAAU,CAAC;IAEpC,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,IAAI,CAAC,IAAI,EAAE,CAAC;QAC5B,MAAM,IAAI,KAAK,CACb,oGAAoG,CACrG,CAAC;IACJ,CAAC;IAED,MAAM,IAAI,GAAG,QAAQ,CAAC,OAAO,CAAC,GAAG,CAAC,UAAU,IAAI,KAAK,EAAE,EAAE,CAAC,CAAC;IAC3D,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,YAAY,KAAK,MAAM,CAAC,CAAC,CAAC,IAAI,KAAK,GAAG,CAAC;IAE7F,MAAM,MAAM,GAAG,SAAS,EAAE,CAAC;IAC3B,MAAM,QAAQ,GAAG,OAAO,CAAC,GAAG,CAAC,eAAe,IAAI,MAAM,CAAC,OAAO,CAAC;IAC/D,MAAM,SAAS,GAAG,OAAO,CAAC,GAAG,CAAC,gBAAgB,IAAI,OAAO,CAAC,GAAG,CAAC,kBAAkB,IAAI,IAAI,CAAC;IAEzF,OAAO;QACL,IAAI;QACJ,IAAI;QACJ,MAAM;QACN,IAAI;QACJ,IAAI;QACJ,QAAQ;QACR,SAAS;KACV,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/config/index.ts"],"names":[],"mappings":"AAAA,cAAc,cAAc,CAAC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
14
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
|
+
};
|
|
16
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
__exportStar(require("./app.config"), exports);
|
|
18
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/config/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,+CAA6B"}
|
package/lib/index.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* LodgeFlow Shared Firebase Functions
|
|
3
|
+
*
|
|
4
|
+
* Common Firebase Cloud Functions modules shared across multiple applications.
|
|
5
|
+
* Each application must initialize the configuration before using any functions.
|
|
6
|
+
*/
|
|
7
|
+
export * from './config';
|
|
8
|
+
export * from './modules/bootstrap';
|
|
9
|
+
export * from './modules/email';
|
|
10
|
+
export * from './modules/storage';
|
|
11
|
+
export * from './modules/user';
|
|
12
|
+
export * from './modules/security';
|
|
13
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,cAAc,UAAU,CAAC;AACzB,cAAc,qBAAqB,CAAC;AACpC,cAAc,iBAAiB,CAAC;AAChC,cAAc,mBAAmB,CAAC;AAClC,cAAc,gBAAgB,CAAC;AAC/B,cAAc,oBAAoB,CAAC"}
|
package/lib/index.js
ADDED
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* LodgeFlow Shared Firebase Functions
|
|
4
|
+
*
|
|
5
|
+
* Common Firebase Cloud Functions modules shared across multiple applications.
|
|
6
|
+
* Each application must initialize the configuration before using any functions.
|
|
7
|
+
*/
|
|
8
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
9
|
+
if (k2 === undefined) k2 = k;
|
|
10
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
11
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
12
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
13
|
+
}
|
|
14
|
+
Object.defineProperty(o, k2, desc);
|
|
15
|
+
}) : (function(o, m, k, k2) {
|
|
16
|
+
if (k2 === undefined) k2 = k;
|
|
17
|
+
o[k2] = m[k];
|
|
18
|
+
}));
|
|
19
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
20
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
21
|
+
};
|
|
22
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
23
|
+
__exportStar(require("./config"), exports);
|
|
24
|
+
__exportStar(require("./modules/bootstrap"), exports);
|
|
25
|
+
__exportStar(require("./modules/email"), exports);
|
|
26
|
+
__exportStar(require("./modules/storage"), exports);
|
|
27
|
+
__exportStar(require("./modules/user"), exports);
|
|
28
|
+
__exportStar(require("./modules/security"), exports);
|
|
29
|
+
//# sourceMappingURL=index.js.map
|
package/lib/index.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;;;;;;;;;;;;;;AAEH,2CAAyB;AACzB,sDAAoC;AACpC,kDAAgC;AAChC,oDAAkC;AAClC,iDAA+B;AAC/B,qDAAmC"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import { BootstrapStatusResult, SystemBootstrapData, SystemBootstrapResult } from './bootstrap.models';
|
|
2
|
+
export declare const systemBootstrap: import("firebase-functions/https").CallableFunction<SystemBootstrapData, Promise<SystemBootstrapResult>, unknown>;
|
|
3
|
+
export declare const checkBootstrapStatus: import("firebase-functions/https").CallableFunction<any, Promise<BootstrapStatusResult>, unknown>;
|
|
4
|
+
//# sourceMappingURL=bootstrap.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bootstrap.d.ts","sourceRoot":"","sources":["../../../src/modules/bootstrap/bootstrap.ts"],"names":[],"mappings":"AAKA,OAAO,EACL,qBAAqB,EACrB,mBAAmB,EACnB,qBAAqB,EACtB,MAAM,oBAAoB,CAAC;AAE5B,eAAO,MAAM,eAAe,mHAwG3B,CAAC;AAEF,eAAO,MAAM,oBAAoB,mGAsC/B,CAAC"}
|