eSellify Documentation
Complete setup and deployment guide for your multi-platform e-classified application.
v1.3 - Flutter + Firebase
💻
Platform
Android, iOS & Web
🔧
Framework
Flutter + Firebase
Key Features
📱
Multi-Platform
Build for Android, iOS, and Web from a single Flutter codebase.
🔐
Authentication
Phone, Google, and Apple sign-in powered by Firebase Authentication.
🛒
Shopping Cart
Full-featured cart with quantity management, coupons, and checkout flow.
🔔
Push Notifications
Real-time notifications via Firebase Cloud Messaging (FCM) on all platforms.
⚙
Admin Panel
Full-featured Flutter web admin dashboard for managing products, orders, and users.
💳
Payment Gateway
Multiple payment integrations including Stripe, Razorpay, PayPal, and COD.
What's Included
- Customer App - Flutter mobile app for Android & iOS
- Seller App - Flutter mobile app for sellers to manage products & orders
- Admin Panel - Flutter web-based admin dashboard
- Database Files - Pre-built Firestore database collections for quick setup
- Firestore Indexes - Optimized query indexes for better performance
- Documentation - This comprehensive setup guide
Live Demo
📝 Demo Credentials
| Platform |
Email |
Password |
| Admin Panel |
admin@esellify.com |
123456 |
Before starting the setup, make sure you have the following tools and accounts ready.
Required Software
| Software |
Version |
Purpose |
| Flutter SDK |
Latest Stable |
Framework for building the app |
| Dart SDK |
Bundled with Flutter |
Programming language for Flutter |
| Android Studio |
Latest |
IDE & Android SDK/Emulator |
| Xcode (macOS only) |
Latest |
iOS development & simulator |
| Firebase CLI |
Latest |
Deploy and manage Firebase services |
| Git |
Latest |
Version control |
| VS Code / Android Studio |
Latest |
Code editor with Flutter/Dart plugins |
Required Accounts
- Google Account - For Firebase Console & Google Cloud
- Firebase Account - Project hosting, database, authentication, and functions
- Payment Gateway Account - Stripe, Razorpay, or PayPal for processing payments
- Apple Developer Account (optional) - Required for iOS deployment & Apple Sign-In
- Google Play Console (optional) - For publishing to Google Play Store
Important:
- Some Firebase features (phone authentication, etc.) require the Blaze plan
(pay-as-you-go). The free Spark plan has limitations.
- Ensure your system meets Flutter's minimum system requirements for your OS.
Follow these steps in order for a smooth setup experience. Each step links to the detailed section below.
Important — please read first:
What you received is the Flutter source code, not a ready-to-upload
website. Uploading the source code directly to your hosting will NOT work. You must:
- Set up Firebase first — create the project, connect it to the apps, and
add the configuration files. The apps will not run or build correctly until Firebase is
configured.
- Generate a build — for the web (Admin Panel / Customer Web) run
flutter build web --release; for Android/iOS build the
APK/AAB or iOS archive.
- Upload only the build output — for web, upload the generated
build/web folder contents to your server (or deploy with Firebase
Hosting). Never upload the raw lib/ source to a web server.
Estimated Setup Time
Following this guide carefully, the complete setup typically takes 1-2 hours
depending on your familiarity with Flutter and Firebase.
To set up Flutter on both Windows and macOS, follow these step-by-step instructions.
Setting Up Flutter on Windows
System Requirements
- Operating System: Windows 10 or later (64-bit)
- Disk Space: At least 2.8 GB (excluding IDE and tools)
- Required Tool: Git for Windows
Download Flutter SDK
- Visit the official Flutter installation page.
- Download the latest stable version of the Flutter SDK (ZIP file).
- Extract the ZIP and move the flutter folder to a preferred location,
e.g., C:\src\flutter.
Add Flutter to System Path
- Open the Start Menu, search for "Environment Variables", and click "Edit the
system environment variables".
- In the System Properties window, click Environment Variables.
- Under User variables, locate the Path variable.
- If it exists, click Edit and append the path to flutter\bin
(e.g., C:\src\flutter\bin) at the end, separated by a semicolon.
- If it doesn't exist, click New, name it Path, and enter the
path to flutter\bin.
Verify Installation
- Open Command Prompt and run:
flutter doctor
- This will analyze your environment and report any missing dependencies (like Android Studio or
toolchains).
Install Android Studio
- Download Android Studio from developer.android.com.
- Launch the installer and complete the setup wizard, which installs:
- Android SDK
- Android SDK Command-line Tools
- Android SDK Build-Tools
- After installation, go to Android Studio > Settings > Plugins and install both
Flutter and Dart plugins.
Set Up an Android Emulator
- Open Android Studio.
- Go to Tools > AVD Manager.
- Follow the prompts to create and configure a new Android Virtual Device (AVD).
Final Setup Check
- Run the following again to ensure everything is configured:
flutter doctor
- Resolve any remaining issues shown in the output.
Setting Up Flutter on macOS
System Requirements
- Operating System: macOS 10.15 (Catalina) or later
- Disk Space: At least 2.8 GB (excluding IDE and tools)
- Required Tools: Git, Xcode (for iOS development)
Download Flutter SDK
Add Flutter to PATH
- Open your shell profile file (.zshrc or .bashrc) and add:
export PATH="$PATH:$HOME/development/flutter/bin"
- Then run source ~/.zshrc (or restart your terminal) to apply the changes.
Install Xcode
- Install Xcode from the Mac App Store.
- After installation, run the following commands to configure Xcode CLI tools:
sudo xcode-select --switch /Applications/Xcode.app/Contents/Developer
sudo xcodebuild -runFirstLaunch
Install CocoaPods
- CocoaPods is required for iOS dependency management:
sudo gem install cocoapods
Verify Installation
flutter doctor
- Resolve any issues reported by Flutter Doctor before proceeding.
eSellify supports three authentication methods. Enable each one in the Firebase Console.
1. Enable Phone Authentication
- Go to the Firebase Console.
- Select your project from the dashboard.
- In the left sidebar, click on "Authentication".
- Navigate to the "Sign-in method" tab.
- Locate "Phone" and click on the edit icon.
- Toggle the switch to Enable phone authentication.
- Click Save.
2. Enable Google Sign-In
- Open the Firebase Console and choose your Firebase project.
- Go to the Authentication section from the sidebar.
- Under the "Sign-in method" tab, find "Google" and click the edit icon.
- Toggle the Enable switch.
- If prompted, configure the OAuth consent screen by providing:
- App name
- Support email
- Developer contact details
- Save your changes.
3. Enable Apple Sign-In
- Visit the Firebase Console and select your project.
- Go to Authentication > Sign-in method.
- Scroll to Apple and click the edit icon.
- Enable the provider and provide the required Apple Developer credentials:
- Team ID (from your Apple Developer account)
- Service ID
- Key ID
- Private Key (.p8 file)
- Save your configuration.
Note:
Apple Sign-In requires an active Apple Developer account ($99/year). It is mandatory for iOS apps
that offer third-party login options.
4. Add Authorized Domains (Required for Web)
For Phone Authentication to work on your web app, you must add your domain to the authorized domains
list in Firebase.
- Go to the Firebase Console.
- Select your project and navigate to Authentication.
- Click on the "Settings" tab.
- Scroll down to "Authorized domains".
- Click "Add domain" and add your web app's domain (e.g., yourdomain.com).
Default domains: localhost and
your-project-id.firebaseapp.com are added automatically. You only need to
add your custom domain (e.g., yourdomain.com) if you are hosting the web
app on your own domain.
eSellify uploads ad photos, profile pictures, verification documents and other media to
Firebase Storage. You must enable Storage and update its security rules before these
features will work.
1. Enable Storage in the Firebase Console
- Open the Firebase Console and
select your project.
- In the left sidebar, click "Build" > "Storage".
- Click "Get started".
- Choose a Cloud Storage location (use the same region as your Firestore database) and
confirm.
- When asked about security rules, select "Start in production mode" — you will
replace the rules in the next step.
- Click Done to finish provisioning the default storage bucket.
Note:
Enabling Cloud Storage requires the project to be on the Blaze (pay-as-you-go) plan if
you are using a recently created Firebase project. A free Spark-plan bucket is sufficient for
development and small deployments.
2. Update the Storage Security Rules
- Inside Storage, open the "Rules" tab.
- Replace the existing rules with the configuration below.
- Click "Publish" to apply.
The following rules let ad images and profile pictures be viewed by everyone (including visitors who are
not logged in, e.g. on the public web listings), while only signed-in users can upload
files:
rules_version = '2';
service firebase.storage {
match /b/{bucket}/o {
match /{allPaths=**} {
allow read: if true; // public read
allow write: if request.auth != null; // only signed-in users can upload
}
}
}
Important:
Never publish open rules such as allow read, write: if true; in production — this
lets anyone upload or delete files in your bucket and can lead to abuse and unexpected billing.
The Customer Web build loads and uploads images (ad photos, profile pictures, verification
documents) directly from your Firebase Storage bucket. Because the website and the storage bucket are on
different domains, the browser blocks these requests unless the bucket has a CORS
(Cross-Origin Resource Sharing) policy that allows your site. Configure CORS once per bucket.
When you need this:
- Images don’t load on the customer web app and the browser console shows errors like
"has been blocked by CORS policy" or "No 'Access-Control-Allow-Origin'
header".
- Uploading a photo from the web app fails while the same action works on the mobile app.
The mobile (Android/iOS) apps are not affected by CORS
— this step is only required for the web build.
1. Install the Google Cloud SDK
- CORS is applied with the gsutil /
gcloud storage command-line tool from the Google Cloud SDK.
- Download and install it from cloud.google.com/sdk/docs/install.
- After installing, authenticate and select your Firebase project (the project ID is the same as in
the Firebase Console):
gcloud auth login
gcloud config set project YOUR_PROJECT_ID
2. Create a cors.json File
- Create a file named cors.json on your computer with the content below.
- Replace the entries in "origin" with the exact domains where your
customer web app runs.
[
{
"origin": [
"https://your-domain.com",
"https://your-project.web.app",
"https://your-project.firebaseapp.com",
"http://localhost:5000"
],
"method": ["GET", "HEAD", "PUT", "POST", "DELETE"],
"responseHeader": ["Content-Type", "Authorization", "Content-Length", "User-Agent", "x-goog-resumable"],
"maxAgeSeconds": 3600
}
]
Tip:
Keep http://localhost:5000 (and any other local port you use, e.g.
http://localhost:8080) while developing, and add your live domain(s)
before going to production. To allow any origin during testing you can use
"origin": ["*"] — but restrict it to your real domains for
production.
3. Apply the CORS Configuration
- Find your storage bucket name — it’s the
storageBucket value in your Firebase config (for example
your-project.firebasestorage.app or
your-project.appspot.com).
- From the same folder as cors.json, run one of the following:
# Newer gcloud CLI
gcloud storage buckets update gs://YOUR_BUCKET_NAME --cors-file=cors.json
# Or the classic gsutil command
gsutil cors set cors.json gs://YOUR_BUCKET_NAME
4. Verify
- Confirm the policy was applied:
gcloud storage buckets describe gs://YOUR_BUCKET_NAME --format="default(cors_config)"
# Or with gsutil
gsutil cors get gs://YOUR_BUCKET_NAME
- Reload the customer web app. Images should now load and uploads should succeed. A hard refresh
(Ctrl/Cmd + Shift + R) helps clear any cached failed requests.
Success:
Your Storage bucket now accepts cross-origin requests from your web app, so media loads and uploads
work correctly in the browser.
Import the pre-built database collections to quickly populate your Firestore database with the required
structure (categories, settings, currencies, subscription packages and more). This is a one-time step
that gets a brand-new project ready to run.
Before you begin:
- You have already created a Firebase project and connected it to the apps
(see Setup Firebase).
- You have the database.zip file that ships with the project package.
- You have Owner or Editor access to the Firebase project.
- Run these steps on a fresh, empty Firestore database. Importing over an existing
database overwrites documents that share the same IDs.
1. Create the Firestore Database
A new Firebase project does not have a database yet — create it first, otherwise the import will
fail.
- Open the Firebase Console and
select your project.
- In the left sidebar, click "Build" > "Firestore Database".
- Click "Create database".
- Choose a location (pick the region closest to your users — this
cannot be changed later).
- Select "Start in test mode" and click "Create".
- Open the "Rules" tab, set the rules below, then click "Publish":
rules_version = '2';
service cloud.firestore {
match /databases/{database}/documents {
match /{document=**} {
allow read, write: if true;
}
}
}
Important:
These open rules (allow read, write: if true;) make the database fully public and are
intended for development and the initial data import only. Before launching, tighten them — for
example, require authentication with allow read, write: if request.auth != null;.
2. Install Node.js and npm
- Visit the official Node.js website: https://nodejs.org
- Download and install the LTS version compatible with your operating system.
- After installation, verify the setup using:
node -v
npm -v
- Both commands should print a version number. If they don't, close and reopen the terminal (or restart
your computer) so the new PATH is picked up.
3. Extract Database Files
- Locate your database.zip file from the project package.
- Extract its contents to a folder on your computer using your OS's built-in zip utility, WinRAR, or
7-Zip.
- You should see files such as import.js (or
import), package.json, a
config.json placeholder, and one or more .json
collection dumps.
4. Open Terminal or Command Prompt
- Navigate into the extracted folder using your terminal:
cd path/to/extracted/folder
- Tip: type cd (with a trailing space) and then drag the extracted folder
onto the terminal window to auto-fill the full path.
5. Generate Firebase Service Account Key
The import script authenticates with a service-account key — this is different from the
client config used inside the apps.
- Go to the Firebase Console.
- Select your project. Click the gear icon (⚙) next to "Project
Overview" in the top-left sidebar.
- Select "Project settings" from the dropdown menu.
- In the Project Settings page, click the "Service accounts" tab at the top (next to
General, Cloud Messaging, Integrations, etc.).
- You will see the Firebase Admin SDK section. Make sure "Node.js" is
selected as the platform (it should be selected by default).
- Click the Generate new private key button at the bottom of the page.
- A confirmation dialog will appear. Click "Generate key".
- A JSON key file will be downloaded automatically to your computer.
- Replace the existing config.json in your extracted folder
with this newly downloaded file, and rename it to config.json.
🔎
Navigation Path: Firebase Console → ⚙ (Gear Icon) → Project Settings
→ Service accounts tab → Firebase Admin SDK → Node.js → Generate new private key
Keep it secret:
The service-account key grants full admin access to your project. Never commit
config.json to a public repository or share it publicly.
6. Install Dependencies
- Inside the extracted database folder, install the import helper package:
npm install firestore-export-import
- If a package.json is present you can simply run
npm install instead to install everything at once.
7. Run the Import Command
- Still inside the extracted folder, run:
node import
- The terminal will print the collections being uploaded. Wait until it finishes without errors.
8. Verify in the Firebase Console
- Return to Build > Firestore Database in the console.
- Confirm that collections such as category,
settings, currencies and
subscription_packages now contain documents.
Success:
Once the import completes, your Firestore database will have all the required collections and
documents. Next, deploy the indexes (see Firestore
Database Indexing) so queries run efficiently.
Common errors:
- "5 NOT_FOUND" / database does not exist — you skipped Step 1; create the
Firestore database first.
- "Could not load the default credentials" / config.json error — the
service-account key is missing or not named exactly config.json (Step
5).
- "command not found: node" — Node.js is not installed or the terminal wasn't
restarted after installing it (Step 2).
- "Cannot find module 'firestore-export-import'" — run the install command in
Step 6 inside the correct folder.
Important Notes:
- Ensure you are inside the correct project directory before running any Firebase CLI
commands.
- You must have sufficient permissions (e.g., Editor or Owner role) in your Firebase
project to deploy indexes.
- Once deployed, Firestore queries will benefit from better performance as they'll
use the optimized indexes.
1. Navigate to Your Firebase Project Folder
- Open your terminal or command prompt.
- Use the cd command to move into your Firestore index project folder:
cd path/to/firestore_index
- Replace path/to/firestore_index with the actual directory path where your
Firestore project files are located.
Step A: Run firebase init
- Inside your project directory, initialize Firebase:
firebase init
- The terminal will display the Firebase ASCII logo and the message:
Terminal Output:
You're about to initialize a Firebase project in this directory:
C:\path\to\your\firestore_index
? Are you ready to proceed? (Y/n)
- Type y and press Enter to proceed.
Step B: Select Firebase Features
- You will see a list of Firebase features. Use the arrow keys to navigate and press
Space to select:
Select this option:
(*) Firestore: Configure security rules and indexes files for Firestore
Use arrow keys to move, Space to select, Enter to confirm.
Step C: Choose Firebase Project
- Select Use an existing project when prompted.
- A list of your Firebase projects will appear. Use the arrow keys to highlight your eSellify project
and press Enter.
Step D: Set Up Firestore Rules and Indexes
- When prompted for the Firestore rules file (firestore.rules), press Enter
to accept the default.
- If the file already exists, type y to overwrite.
- When prompted for the Firestore indexes file (firestore.indexes.json),
press Enter to accept the default. Overwrite if asked.
- You will see the message: Firebase initialization complete!
Step E: Deploy Firestore Indexes
- Now deploy the indexes defined in firestore.indexes.json:
firebase deploy --only firestore:indexes
Deployment Complete
- You should see the following output in your terminal:
Expected Terminal Output:
=== Deploying to 'your-project-id'...
i firestore: reading indexes from firestore.indexes.json...
i cloud.firestore: checking firestore.rules for compilation errors...
+ cloud.firestore: rules file firestore.rules compiled successfully
i firestore: deploying indexes...
+ firestore: deployed indexes in firestore.indexes.json successfully
+ Deploy complete!
Project Console: https://console.firebase.google.com/project/your-project-id/overview
eSellify uses Firebase Cloud Functions to send transactional emails. Follow these steps
to deploy them on a fresh Firebase project.
Step 1: Prerequisites
- Node.js v22+ — Download from
nodejs.org. Verify with:
node --version
- Firebase CLI — Install globally:
npm install -g firebase-tools
- Firebase Login — Run firebase login and
authenticate with your Google account.
Blaze Plan Required: Cloud Functions require the
Blaze (Pay as you go)
plan. Upgrade in
Firebase Console
> your project >
Upgrade. The Blaze plan still includes generous free tiers.
Step 2: Set Your Firebase Project ID
Open function/.firebaserc and replace the project ID with yours:
{
"projects": {
"default": "your-firebase-project-id"
}
}
Find your Project ID:
Firebase Console >
Project Settings (gear icon) >
General tab.
Step 3: Install Dependencies
Open a terminal in the project root and run:
cd function/functions
npm install
Node version must match: The "node": "22" in
functions/package.json must match your local Node.js version. If you have
Node 20, change it to "20".
Step 4: Deploy
Navigate back to the function directory and deploy:
cd ..
firebase deploy --only functions
Expected output on success:
i functions: preparing codebase default for deployment
+ functions: functions source uploaded successfully
i functions: creating Node.js 22 (2nd Gen) function sendSmtpTestEmail(us-central1)...
i functions: creating Node.js 22 (2nd Gen) function sendTransactionalEmail(us-central1)...
+ functions[sendSmtpTestEmail(us-central1)] Successful create operation.
+ functions[sendTransactionalEmail(us-central1)] Successful create operation.
+ Deploy complete!
First deployment may take 2–5 minutes as Firebase builds the container image.
Subsequent deployments are faster.
Step 5: Verify Deployment
Confirm both functions are live:
firebase functions:list
You should see:
+------------------------+---------+----------+-------------+--------+----------+
| Function | Version | Trigger | Location | Memory | Runtime |
+------------------------+---------+----------+-------------+--------+----------+
| sendSmtpTestEmail | v2 | callable | us-central1 | 256 | nodejs22 |
+------------------------+---------+----------+-------------+--------+----------+
| sendTransactionalEmail | v2 | callable | us-central1 | 256 | nodejs22 |
+------------------------+---------+----------+-------------+--------+----------+
Deploying a Single Function (Optional)
To redeploy only one function after making changes:
firebase deploy --only functions:sendTransactionalEmail
Checking Logs
If something isn't working, check the function logs:
firebase functions:log --only sendTransactionalEmail
You can also view logs in the
Firebase Console >
Functions > Logs tab.
Here you will find all the setup guides for Admin Panel configuration.
Important Notes:
- Some Firebase features require the Blaze plan.
- If you are on the free Spark plan, please upgrade to Blaze Plan for full
functionality.
Update HTML Title
- Open: web/index.html
- Inside the <head> section, update the content of the <title> tag:
<head>
...
<title>Your New App Name</title>
...
</head>
1. Install Firebase CLI Tools
npm install -g firebase-tools
2. Authenticate Firebase CLI
firebase login
- A browser window will open to complete authentication with your Google account.
3. Create a Firebase Project
- Create a project directly from the terminal:
firebase projects:create
OR
- Create one via the Firebase
Console.
- Enter a name and press Continue, then click Create Project.
- Now add an app in Firebase:
1
Add Firebase to your Flutter App:
- On the Firebase Project Overview page, you will see the text "Get started by adding
Firebase to your app" with platform icons (iOS, Android, Web, Unity, Flutter).
- Click the Flutter icon (the last icon, looks like a diamond shape).
- Firebase will show the "Add Firebase to your Flutter app" wizard with two commands.
2
Run the FlutterFire CLI commands shown in the wizard:
$ dart pub global activate flutterfire_cli
$ flutterfire configure --project=YOUR_PROJECT_ID
This automatically registers your per-platform apps with Firebase and adds a lib/firebase_options.dart configuration file to your Flutter project.
- After running both commands, click Next in the Firebase wizard.
- Then click Continue to console.
4. Initialize Firebase in Your Flutter App
- Open Android Studio and go to the Terminal tab.
- Run the initialization commands:
dart pub global activate flutterfire_cli
flutterfire configure --project=YOUR_PROJECT_ID
- The CLI will ask which platforms you want to configure. Since this is the Admin Panel:
Platform Selection (Admin Panel = Web only):
? Which platforms should your configuration support?
( ) android
( ) ios
( ) macos
(*) web <-- Select ONLY this
( ) windows
Use arrow keys and Space to select web only. Press Enter to confirm.
- When asked "firebase_options.dart already exists. Do you want to override it?", type
yes and press Enter.
- Setup is complete when you see: Firebase configuration file
lib/firebase_options.dart generated successfully.
1. Generate a Google Maps API Key
- Go to the Google Cloud Console.
- Create a new project or select an existing one.
- Enable the following APIs for your project:
- Maps SDK for Android
- Maps SDK for iOS
- Maps JavaScript API
- Go to APIs & Services > Credentials.
- Click "Create Credentials" > "API key".
- Copy the newly generated API key.
2. Add API Key to Flutter Web
- Open: web/index.html
- Inside the <head> section, add:
<script src="https://maps.googleapis.com/maps/api/js?key=YOUR_API_KEY&libraries=places"></script>
Flutter Web
For Flutter web, the favicon represents your application in the browser tab.
Replace Favicon:
- Design your favicon in the proper size and format (typically favicon.ico
or PNG, 32x32 or 16x16 pixels).
- Go to your Flutter project's web/ directory.
- Replace the existing favicon.png or favicon.ico with your own file using the same filename to
maintain the reference.
Tip:
You can use online tools like favicon.io or
realfavicongenerator.net to generate favicons from your logo in all required sizes.
Important:
Do not upload the source code to your server — it will not work. Complete the
Firebase setup first, then run flutter build web
--release and upload only the generated build/web/ folder.
Note:
Run all commands below from the project folder in your Android Studio terminal or system terminal.
1. Create the Build for Server Upload
- Run the following commands in order:
flutter clean
flutter pub get
flutter build web --release
- You will see output like:
Compiling lib/main.dart for the Web...
✓ Built build\web 19.5s
- After running the above commands, Flutter generates the optimized build inside:
build/web/
- Upload the contents of the build/web/ folder to your server or hosting
provider (via FTP, cPanel, or SSH).
Note:
Run all commands below from the project folder in your terminal.
1. Build and Deploy Using Firebase Hosting
- Install Firebase CLI (if not already installed):
npm install -g firebase-tools
firebase login
- Initialize Firebase inside your project folder:
firebase init
Follow the Firebase Init prompts:
? Are you ready to proceed? (Y/n) y
? Which Firebase features do you want to set up?
(*) Hosting: Configure files for Firebase Hosting
and (optionally) set up GitHub Action deploys
=== Project Setup
? Please select an option: Use an existing project
i Using project your-project-id
=== Hosting Setup
? What do you want to use as your public directory? build/web
? Configure as a single-page app (rewrite all urls to /index.html)? Yes
? Set up automatic builds and deploys with GitHub? No
- You should see: + Firebase initialization complete!
- Now build the release version:
flutter build web --release
- Then deploy to Firebase Hosting:
firebase deploy
Expected Deployment Output:
=== Deploying to 'esellify-app'...
i deploying firestore, hosting
i hosting[esellify-app]: beginning deploy...
i hosting[esellify-app]: found 516 files in build/web
+ hosting[esellify-app]: file upload complete
+ hosting[esellify-app]: version finalized
+ hosting[esellify-app]: release complete
+ Deploy complete!
Project Console: https://console.firebase.google.com/project/esellify-app/overview
Hosting URL: https://esellify-app.web.app
Success:
Your Admin Panel is now live! Copy the Hosting URL shown in the output (e.g., https://esellify-app.web.app) to access your deployed admin panel.
The customer_web module is the responsive Flutter web build of the
customer application — same Firebase backend as the mobile app, same business logic, but
redesigned for desktop/tablet browsers with a header + footer shell. Follow the steps below to
configure and deploy it.
Important Notes:
- The customer web uses the same Firebase project as your admin panel and
mobile apps.
- Some features (App Check, flutter_local_notifications) are mobile-only and are
auto-skipped on web via kIsWeb guards already in the code.
1. Update HTML Title & Meta
- Open: customer_web/web/index.html
- Inside the <head> section, update the following tags:
<title>Your New App Name</title>
<meta name="description" content="Your short app description">
<meta name="apple-mobile-web-app-title" content="Your App Name">
2. Update PWA Manifest
- Open: customer_web/web/manifest.json
- Update the name, short_name, and
description fields:
{
"name": "Your App Name",
"short_name": "AppShort",
"description": "Your app description",
"theme_color": "#3068FF",
...
}
Customer Web needs Firebase credentials in three places. All three must use
the same web app from your Firebase project.
1. Get Your Firebase Web Config
- Go to the Firebase Console
→ your project → ⚙ Project Settings → General tab.
- Scroll to "Your apps". If you do not have a Web app yet, click
"Add app" → select the Web icon (</>) → register
it.
- Copy the firebaseConfig values (apiKey, authDomain, projectId,
storageBucket, messagingSenderId, appId, measurementId).
2. Update web/index.html
- Open: customer_web/web/index.html
- Find the window.firebaseConfig object and paste your values:
window.firebaseConfig = {
apiKey: "YOUR_API_KEY",
authDomain: "YOUR_PROJECT.firebaseapp.com",
projectId: "YOUR_PROJECT_ID",
storageBucket: "YOUR_PROJECT.firebasestorage.app",
messagingSenderId: "YOUR_SENDER_ID",
appId: "YOUR_APP_ID",
measurementId: "YOUR_MEASUREMENT_ID"
};
3. Update web/firebase-messaging-sw.js
- Open: customer_web/web/firebase-messaging-sw.js
- Paste the same config inside firebase.initializeApp({...}).
This file handles background push notifications and needs its own copy.
4. Update lib/firebase_options.dart
- Open: customer_web/lib/firebase_options.dart
- Find static const FirebaseOptions web = ... and replace the
values:
static const FirebaseOptions web = FirebaseOptions(
apiKey: 'YOUR_API_KEY',
appId: 'YOUR_APP_ID',
messagingSenderId: 'YOUR_SENDER_ID',
projectId: 'YOUR_PROJECT_ID',
authDomain: 'YOUR_PROJECT.firebaseapp.com',
storageBucket: 'YOUR_PROJECT.firebasestorage.app',
measurementId: 'YOUR_MEASUREMENT_ID',
);
⚠️ All three must match
Flutter reads from firebase_options.dart, while the JS SDK in
index.html and the background service worker
firebase-messaging-sw.js read their own copies. If the three
are not identical you will get authentication errors or silent FCM failures.
Customer Web uses Google Maps for the location picker, address selection, and ad-detail map
embed. If you already created a Google Maps API key for your admin panel or mobile app, you
can reuse it — just make sure the key has the Maps JavaScript API and
Places API enabled and is not restricted to a different referrer.
1. Enable Required APIs
- Go to the Google Cloud Console
→ APIs & Services → Library.
- Search and Enable:
- Maps JavaScript API
- Places API
- Geocoding API
2. Add Your API Key to web/index.html
- Open: customer_web/web/index.html
- Inside the <head>, add (replace YOUR_API_KEY):
<script src="https://maps.googleapis.com/maps/api/js?key=YOUR_API_KEY&libraries=places"></script>
3. Restrict the Key (Recommended)
- In the Cloud Console → Credentials → click your API key.
- Under Application restrictions, choose HTTP referrers and add
your domains (e.g. *.your-domain.com/*,
your-project.web.app/*).
- Under API restrictions, restrict to only the APIs listed above.
Note:
Run all commands from the customer_web/ folder.
1. Install Dependencies
flutter clean
flutter pub get
2. Launch in Chrome
flutter run -d chrome
- Chrome will open automatically at a local URL like
http://localhost:8080.
- The app uses clean path URLs (e.g. /ad-listing-detail,
/ads-listing) — no #-hash
fragments.
3. Optional: Custom Port
flutter run -d chrome --web-port 5000
Important:
Do not upload the source code to your server — it will not work. Configure
Firebase first, then build with flutter
build web --release and upload only the generated
customer_web/build/web/ folder.
Note:
Run all commands from the customer_web/ folder.
1. Build the Release Bundle
flutter clean
flutter pub get
flutter build web --release
- The optimized build will be generated in:
customer_web/build/web/
2. Deploy Option A: Any Web Server (FTP / cPanel / Nginx)
- Upload the entire contents of build/web/ to your server's
public HTML directory.
- For path URL strategy to work, configure your server to serve index.html
for all routes.
Apache .htaccess example:
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.html$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.html [L]
</IfModule>
Nginx example:
location / {
try_files $uri $uri/ /index.html;
}
3. Deploy Option B: Firebase Hosting
- Install the Firebase CLI (if you haven't yet):
npm install -g firebase-tools
- Login and initialize hosting inside the customer_web/ folder:
firebase login
firebase init hosting
Follow the prompts:
? Please select an option: Use an existing project
? Select a default Firebase project: your-project-id
? What do you want to use as your public directory? build/web
? Configure as a single-page app (rewrite all urls to /index.html)? Yes
? Set up automatic builds and deploys with GitHub? No
? File build/web/index.html already exists. Overwrite? No
⚠️ Answer "No" to overwriting index.html
Always answer No when asked to overwrite existing
build/web/index.html — otherwise Firebase will replace
your custom index.html (with the Firebase JS SDK + reCAPTCHA
container) with a blank template and the app will fail to initialize.
- Build the release bundle and deploy:
flutter build web --release
firebase deploy --only hosting
Success:
Your Customer Web is now live. The deploy command will print a Hosting URL
(e.g. https://your-project.web.app) — that's your
production URL.
4. Post-Deploy Checklist
- Add your deployed domain to Firebase Authentication → Settings
→ Authorized domains so Google / Apple sign-in works.
- Add the domain as an HTTP referrer on your Google Maps API key restriction.
- Verify the path URLs work: visit
https://your-project.web.app/ads-listing directly — it
should load the listing page (not a 404).
Here you will find all the setup guides for configuring the Customer & Seller Apps (Android &
iOS).
Changing the package name of a Flutter project involves updating multiple files and configurations for
both Android and iOS platforms.
Android
Update the applicationId in build.gradle:
- Open: android/app/build.gradle
- Inside the defaultConfig block, find and replace the applicationId:
defaultConfig {
applicationId "com.new.package.name"
}
Rename Java Package Directories:
- Go to: android/app/src/main/java/
- Rename the directory folders to match your new package structure (e.g., com/new/package/name).
- Make sure the new folder path matches the applicationId you set above.
Update AndroidManifest.xml:
- Open: android/app/src/main/AndroidManifest.xml
- Update the package attribute in the root <manifest> tag:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.new.package.name">
</manifest>
Update Other Manifest Files:
- Also update the package attribute in:
- android/app/src/debug/AndroidManifest.xml
- android/app/src/profile/AndroidManifest.xml
iOS
Update PRODUCT_BUNDLE_IDENTIFIER in Xcode:
- Open the iOS project in Xcode: ios/Runner.xcworkspace
- Select the Runner target, then go to the Build Settings tab.
- Search for PRODUCT_BUNDLE_IDENTIFIER.
- Replace it with your new bundle identifier (e.g., com.new.package.name).
Update Bundle Identifier in Info.plist:
- Open: ios/Runner/Info.plist
- Locate the CFBundleIdentifier key and update its value.
Prerequisites
- Flutter SDK is installed
- A Flutter project is already created
- You understand the basic Flutter project structure
Android
Update AndroidManifest.xml:
- Navigate to: android/app/src/main/AndroidManifest.xml
- Find the application tag and modify the android:label attribute:
<application
android:name="${applicationName}"
android:icon="@mipmap/ic_launcher"
android:label="Your App Name"
...>
</application>
Update strings.xml:
- Open: android/app/src/main/res/values/strings.xml
- Update the app_name string:
<string name="app_name">Your New App Name</string>
iOS
Update Info.plist:
- Go to: ios/Runner/Info.plist
- Locate the key for CFBundleName and change its value:
<key>CFBundleName</key>
<string>Your New App Name</string>
Update Display Name in Xcode:
- Open your project in Xcode: ios/Runner.xcworkspace
- Select the Runner target, click the General tab.
- Find the Display Name field and update it to your desired app name.
Android
Replace Default Icons:
- Create your custom app icons in various densities. Navigate to: android/app/src/main/res/
- Replace ic_launcher.png in each of these folders with your custom icon:
- mipmap-mdpi (48x48 px)
- mipmap-hdpi (72x72 px)
- mipmap-xhdpi (96x96 px)
- mipmap-xxhdpi (144x144 px)
- mipmap-xxxhdpi (192x192 px)
Update Icon Reference in AndroidManifest.xml:
- Open: android/app/src/main/AndroidManifest.xml
- Ensure the android:icon points to your custom icon:
<application
android:icon="@mipmap/ic_launcher"
...>
</application>
iOS
Replace AppIcon Set:
- Prepare your custom icons in iOS-specific sizes and formats.
- Replace the contents of: ios/Runner/Assets.xcassets/AppIcon.appiconset/
- Ensure your icon set follows Apple's size and naming requirements.
Tip:
Use tools like appicon.co or the flutter_launcher_icons
package to automatically generate all required icon sizes from a single source image.
Note:
This setup applies to both the Admin Panel, Customer App, and Seller App. The steps are identical.
1. Install Firebase CLI Tools
npm install -g firebase-tools
2. Authenticate Firebase CLI
firebase login
- A browser window will open to complete authentication with your Google account.
3. Create a Firebase Project
firebase projects:create
OR
- Create one via the Firebase
Console.
- Enter a name and press Continue, then click Create Project.
- Add your app in Firebase:
➤
On the Project Overview page, click the Flutter icon under "Get started by adding
Firebase to your app". The wizard will show two commands to run:
$ dart pub global activate flutterfire_cli
$ flutterfire configure --project=YOUR_PROJECT_ID
Run both in your project terminal. Then click Next → Continue to console.
4. Initialize Firebase in Your Flutter App
- Open Android Studio and go to the Terminal tab. Run:
dart pub global activate flutterfire_cli
flutterfire configure --project=YOUR_PROJECT_ID
- The CLI will ask which platforms to configure. For the Customer/Seller App:
Platform Selection (Customer/Seller App = Android & iOS):
? Which platforms should your configuration support?
(*) android <-- Select this
(*) ios <-- Select this
( ) macos
( ) web
( ) windows
Use arrow keys and Space to select android and ios. Press Enter.
- If prompted "firebase_options.dart already exists. Do you want to override it?", type
yes.
- Setup is complete when you see:
Firebase configuration file lib/firebase_options.dart generated successfully
with the following Firebase apps:
Platform Firebase App Id
android 1:XXXXXXXXX:android:XXXXXXXXX
ios 1:XXXXXXXXX:ios:XXXXXXXXX
1. Create a Firebase Project
- Go to the Firebase Console.
- Click "Add project" and follow the guided steps.
- After setup, you'll be redirected to the Firebase project dashboard.
2. Add Your Flutter App to Firebase
Android Setup:
- Click on the Android icon to register an Android app.
- Enter your Android package name (found in android/app/src/main/AndroidManifest.xml).
- Download the google-services.json file.
- Place it in: android/app/
iOS Setup:
- Click on the iOS icon to register your iOS app.
- Enter your iOS bundle ID (found in Xcode project settings).
- Download the GoogleService-Info.plist file.
- In Xcode:
- Open ios/Runner.xcworkspace.
- Drag and drop GoogleService-Info.plist into the Runner project (check
"Copy items if needed").
3. Add Firebase Packages
- Add the necessary Firebase packages to pubspec.yaml:
dependencies:
firebase_core: ^latest
firebase_auth: ^latest
cloud_firestore: ^latest
flutter pub get
4. Configure DefaultFirebaseOptions
- Use the FlutterFire CLI to auto-generate the configuration file:
flutterfire configure
- This creates lib/firebase_options.dart with platform-specific
configurations.
5. Initialize Firebase in main.dart
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Firebase.initializeApp(
options: DefaultFirebaseOptions.currentPlatform,
);
runApp(MyApp());
}
1. Generate a Google Maps API Key
- Go to the Google Cloud Console.
- Create a new project or select an existing one.
- Enable the following APIs:
- Maps SDK for Android
- Maps SDK for iOS
- Maps JavaScript API
- Places API
- Geocoding API
- Go to APIs & Services > Credentials.
- Click "Create Credentials" > "API key".
- Copy the generated API key.
2. Add API Key - Android
- Open: android/app/src/main/AndroidManifest.xml
- Inside the <application> tag, add:
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="YOUR_API_KEY"/>
3. Add API Key - iOS
- Open: ios/Runner/AppDelegate.swift
- In the application(_:didFinishLaunchingWithOptions:) method, add:
import GoogleMaps
GMSServices.provideAPIKey("YOUR_API_KEY")
Security Tip:
- Restrict your API key in the Google Cloud Console to specific apps (using package name/bundle
ID) and specific APIs to prevent unauthorized usage.
SHA keys are required for Firebase services like Google Sign-In and Phone Authentication on Android.
1. Generate SHA Keys
For Windows (Debug Keystore):
keytool -list -v -keystore "%USERPROFILE%\.android\debug.keystore" -alias androiddebugkey -storepass android -keypass android
For macOS/Linux (Debug Keystore):
keytool -list -v -keystore ~/.android/debug.keystore -alias androiddebugkey -storepass android -keypass android
- Look for the SHA1 and SHA256 values in the output and copy them.
2. Add SHA Keys to Firebase Console
- Open the Firebase Console and
select your project.
- Click the gear icon (⚙) next to "Project Overview" and select "Project
settings".
- Go to the "General" tab (first tab at the top).
- Scroll down to the "Your apps" section. Find your Android app.
- Under your Android app, you will see a section listing existing SHA certificate fingerprints (SHA-1
and SHA-256).
- Click the "Add Fingerprint" button.
- A dialog will appear with a "Certificate fingerprint" input field and toggle buttons
for SHA1 and SHA256.
- Paste your SHA-1 key, select SHA1, and click Save.
- Repeat for the SHA-256 key: click "Add Fingerprint" again, paste the SHA-256 key, select
SHA256, and click Save.
🔎
Navigation Path: Firebase Console → ⚙ Gear Icon → Project Settings
→ General tab → Your apps → Android app → Add Fingerprint
Important Notes:
- For release builds, use your custom release keystore (not the default debug
one).
- Keep your keystore file secure and never expose it publicly.
- You must regenerate SHA keys if you change your signing configuration or keystore.
Before generating a release APK or AAB, you must set up a release keystore and configure
your Gradle build to use it. This is required for publishing to the Google Play Store.
1. Generate a Release Keystore
Run the following command in your terminal to create a new keystore file. Replace the
placeholder values with your own information:
For Windows:
keytool -genkey -v -keystore %USERPROFILE%\upload-keystore.jks -storetype JKS -keyalg RSA -keysize 2048 -validity 10000 -alias upload
For macOS / Linux:
keytool -genkey -v -keystore ~/upload-keystore.jks -storetype JKS -keyalg RSA -keysize 2048 -validity 10000 -alias upload
- You will be prompted to set a keystore password and a key password.
Remember both — you will need them in the next step.
- You will also be asked for your name, organization, city, etc. Fill these in as appropriate.
- The generated file (upload-keystore.jks) is your release keystore.
Keep it safe and never commit it to version control.
2. Create key.properties
Create a file named key.properties inside the
android/ folder of your Flutter project. Paste the following contents
and replace the placeholder values:
storePassword=YOUR_KEYSTORE_PASSWORD
keyPassword=YOUR_KEY_PASSWORD
keyAlias=upload
storeFile=/path/to/your/upload-keystore.jks
- storePassword — The password you set when generating the keystore.
- keyPassword — The key password (often the same as storePassword).
- keyAlias — The alias you used (default: upload).
- storeFile — The absolute path to your
upload-keystore.jks file.
Example (Windows): C:\\Users\\YourName\\upload-keystore.jks
Example (macOS): /Users/YourName/upload-keystore.jks
⚠️ Security Warning
Never commit key.properties or your .jks
keystore file to Git. Add both to your .gitignore:
android/key.properties
*.jks
3. Configure Gradle for Release Signing
Open android/app/build.gradle and add the following changes:
Step A: Load the key.properties file (add above the android { block):
def keystoreProperties = new Properties()
def keystorePropertiesFile = rootProject.file('key.properties')
if (keystorePropertiesFile.exists()) {
keystoreProperties.load(new FileInputStream(keystorePropertiesFile))
}
Step B: Add the signingConfigs block (inside the android { block, before buildTypes):
signingConfigs {
release {
keyAlias keystoreProperties['keyAlias']
keyPassword keystoreProperties['keyPassword']
storeFile keystoreProperties['storeFile'] ? file(keystoreProperties['storeFile']) : null
storePassword keystoreProperties['storePassword']
}
}
Step C: Update buildTypes to use the release signing config:
buildTypes {
release {
signingConfig signingConfigs.release
}
}
4. Generate Release SHA Keys
After creating your release keystore, generate the SHA-1 and SHA-256
keys for the release keystore and add them to Firebase (same process as the debug keys above):
keytool -list -v -keystore /path/to/upload-keystore.jks -alias upload
- Enter your keystore password when prompted.
- Copy the SHA1 and SHA256 values and add them as new fingerprints in
Firebase Console (see Generate SHA Keys section above).
🔎
Quick Reference:
- keytool -genkey ... → creates upload-keystore.jks
- Create android/key.properties with passwords + path
- Load in build.gradle → add signingConfigs.release → reference in buildTypes.release
- Generate release SHA keys → add to Firebase Console
Note:
Run all commands from your project folder in the terminal.
1. Generate APK (for direct installation)
flutter clean
flutter pub get
flutter build apk --release
- The release APK will be generated at:
build/app/outputs/flutter-apk/app-release.apk
2. Generate AAB (for Google Play Store)
flutter clean
flutter pub get
flutter build appbundle --release
- The release AAB file will be generated at:
build/app/outputs/bundle/release/app-release.aab
Difference between APK and AAB:
- APK: Universal package for direct installation or testing on devices.
- AAB: Optimized format required by Google Play Store. It generates smaller,
device-specific APKs automatically.
Using Command-Line Interface (CLI)
Open Terminal and navigate to your project:
cd path/to/your_flutter_project
Run the Flutter App:
flutter run
- This builds and runs your app on a connected device or emulator.
Using Android Studio
- Launch Android Studio and open your Flutter project.
- Click the green Run button in the toolbar.
- Choose your emulator or physical device from the device dropdown.
- Android Studio will build and launch your app automatically.
Using Visual Studio Code
- Launch VS Code and use File > Open Folder to open your Flutter project.
- Press Ctrl + Shift + P (or Cmd + Shift + P on
macOS) to open the Command Palette.
- Search for and select Flutter: Run.
- Choose your emulator or connected device from the list.
Useful Flutter Commands:
- flutter devices - List all connected devices
- flutter run -d chrome - Run on Chrome (web)
- flutter run -d <device_id> - Run on a specific device
- flutter run --release - Run in release mode
1. Get Notification Sender ID
- Open the Firebase Console.
- Click the gear icon (⚙) next to "Project Overview" → "Project
settings".
- Click the "Cloud Messaging" tab at the top.
- Under "Firebase Cloud Messaging API (V1)" (should show Enabled), you will see a "Sender ID" field.
- Copy the Sender ID value (a numeric string).
🔎
Navigation Path: ⚙ Gear Icon → Project Settings → Cloud Messaging tab
→ Sender ID
2. Get Web Push Certificate (VAPID Key)
- Stay on the same Cloud Messaging tab in Project Settings.
- Scroll down to the "Web configuration" section.
- You will see "Web Push certificates" with a description about Application Identity key
pairs.
- If no key pair exists, click Generate key pair.
- Once generated, you will see a table with columns: Key pair, Date added,
Status, Actions.
- Copy the long string under the "Key pair" column — this is your VAPID
Key (Web Push certificate key).
🔎
Navigation Path: Project Settings → Cloud Messaging tab → Web configuration
→ Web Push certificates → Copy Key pair
3. Get Web Client ID (for Google Sign-In)
- In the Firebase Console left sidebar, go to Authentication.
- Click the "Sign-in method" tab.
- Find "Google" in the providers list and click the edit (pencil) icon.
- In the Google provider settings, you will see a collapsed section called "Web SDK
configuration".
- Click on it to expand. You will see two fields:
- Web client ID — Copy this value
- Web client secret
- Copy the Web client ID for use in the Admin Panel.
🔎
Navigation Path: Authentication → Sign-in method → Google (edit) → Web
SDK configuration → Web client ID
4. Get Firebase Service Account JSON File
- Go to Project Settings (gear icon) → "Service accounts" tab.
- You will see the Firebase Admin SDK section with a code snippet.
- Click the Generate new private key button at the bottom.
- A JSON file will be downloaded automatically. Keep this file safe — you will upload it to the
Admin Panel.
🔎
Navigation Path: ⚙ Gear Icon → Project Settings → Service accounts tab
→ Generate new private key
5. Add All Keys in Admin Panel
- Open your Admin Panel (the deployed web app).
- In the left sidebar, go to Settings (expand it).
- Click "General Settings" or "Notification Settings".
- You will see a settings page with the following fields to fill:
Admin Panel → Settings → Notification Settings:
| Field |
What to Enter |
| Notification Sender Key |
The Sender ID copied from Cloud Messaging tab |
| Web Notification Key |
The VAPID Key copied from Web Push certificates |
| Client ID for Google Login |
The Web client ID from Authentication → Google |
| Upload JSON File |
The Service Account JSON file downloaded from Firebase |
- Fill in all fields and upload the JSON file.
- Click Save to apply the settings.
1. Add Notification Key in Admin Panel
- Refer to the Notification Setup section above.
- Make sure you have added the Web Notification Key in the Admin Panel.
2. Configure Firebase Messaging in Flutter Web
- Go to your project folder: web/
- Ensure the file firebase-messaging-sw.js exists. This file handles
background notifications for the web app.
How to get Firebase config values:
- Go to Firebase Console → Project Settings (⚙) → General tab.
- Scroll down to "Your apps" section. Under your Web app, you will see the Firebase
SDK snippet with a firebaseConfig object containing your keys.
Update firebase-messaging-sw.js:
- Open web/firebase-messaging-sw.js in your code editor.
- Replace the Firebase configuration values with your own project's config:
// Give the service worker access to Firebase Messaging.
importScripts('https://www.gstatic.com/firebasejs/10.7.1/firebase-app-compat.js');
importScripts('https://www.gstatic.com/firebasejs/10.7.1/firebase-messaging-compat.js');
// Your Firebase Config
firebase.initializeApp({
apiKey: "YOUR_API_KEY",
authDomain: "YOUR_AUTH_DOMAIN",
projectId: "YOUR_PROJECT_ID",
storageBucket: "YOUR_STORAGE_BUCKET",
messagingSenderId: "YOUR_MESSAGING_SENDER_ID",
appId: "YOUR_APP_ID",
measurementId: "YOUR_MEASUREMENT_ID"
});
const messaging = firebase.messaging();
- Replace each YOUR_* placeholder with the actual values from your Firebase
project settings.
💡 One config, all pages
Firebase credentials for the Landing Page are now stored in one shared file:
landing-page/firebase-config.js. This single file is automatically used
by index.html, privacy-policy.html, and
terms-and-conditions.html — so you only need to update your
credentials in one place.
1. Open the Shared Firebase Config File
- Open the file landing-page/firebase-config.js in your code editor
(VS Code, Android Studio, etc.).
- Inside, you'll find a firebaseConfig object that looks like this:
// landing-page/firebase-config.js
var firebaseConfig = {
apiKey: "YOUR_API_KEY",
authDomain: "YOUR_AUTH_DOMAIN",
projectId: "YOUR_PROJECT_ID",
storageBucket: "YOUR_STORAGE_BUCKET",
messagingSenderId: "YOUR_MESSAGING_SENDER_ID",
appId: "YOUR_APP_ID",
measurementId: "YOUR_MEASUREMENT_ID"
};
2. Get Firebase Credentials
- Go to the Firebase Console.
- Select your project. Click on the gear icon (⚙) next to "Project Overview" in the
left sidebar.
- Select "Project settings".
- In the "General" tab, scroll down to "Your apps" section.
- Under Web apps, you will see your registered web app (e.g., "admin_panel
(web)").
- Below it, you will see the Firebase SDK snippet with the firebaseConfig object containing all your keys (apiKey, authDomain,
projectId, etc.).
No Web App shown?
If no Web App is listed, click "Add app" → select the Web icon
(</>) → enter a nickname → click "Register app". The
firebaseConfig will then appear.
3. Replace the Config
- Copy the values from the firebaseConfig object in the Firebase Console.
- Open landing-page/firebase-config.js.
- Replace the existing values inside firebaseConfig with your copied
values.
- Save the file. That's it — all three HTML pages
(index.html, privacy-policy.html,
terms-and-conditions.html) will automatically pick up the new
credentials. No other files need to be edited.
⚠️ Do not add firebase.initializeApp() to individual HTML files
The shared firebase-config.js already calls
firebase.initializeApp() and exposes
window.db for every page. Duplicating the init call inside
index.html or any other HTML file will cause a
"Firebase App named '[DEFAULT]' already exists" error.
🔎
Navigation Path: Firebase Console → ⚙ Gear Icon → Project Settings
→ General tab → Your apps → Web app → SDK setup and configuration → Copy
firebaseConfig → Paste into landing-page/firebase-config.js
This section applies to Admin Panel and Customer Web when
hosted on Hostinger, cPanel, or any shared Apache / LiteSpeed hosting. It fixes the three most
common problems: changes not reflecting after re-upload, direct URLs returning 404, and blank
white pages.
Upload the build, not the source:
You can only upload a compiled build to shared hosting. Set up Firebase, run
flutter build web --release, and upload the contents of the
build/web/ folder — uploading the project source code will not
work.
⚠️ Why changes don't reflect after upload
- Flutter's service worker (flutter_service_worker.js)
aggressively caches the old build. Visitors keep seeing the old version until the cache
is busted.
- Hostinger's LiteSpeed cache caches index.html
at the server level.
- Browser caching of main.dart.js and other
assets.
1. Add an .htaccess file to your web folder
Create a file named .htaccess inside your project's
web/ folder (so Flutter copies it into
build/web/ on every build) with the following contents:
# ── SPA route rewrite ─────────────────────────────────
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /
RewriteRule ^index\.html$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.html [L]
</IfModule>
# ── Never cache index.html and service worker ─────────
<IfModule mod_headers.c>
<FilesMatch "^(index\.html|flutter_service_worker\.js|flutter_bootstrap\.js|manifest\.json)$">
Header set Cache-Control "no-store, no-cache, must-revalidate, max-age=0"
Header set Pragma "no-cache"
Header set Expires "0"
</FilesMatch>
# Long cache for hashed static assets
<FilesMatch "\.(js|wasm|woff2?|ttf|otf|png|jpg|jpeg|gif|svg|ico)$">
Header set Cache-Control "public, max-age=31536000, immutable"
</FilesMatch>
</IfModule>
# ── Gzip compression ──────────────────────────────────
<IfModule mod_deflate.c>
AddOutputFilterByType DEFLATE text/html text/plain text/css text/javascript application/javascript application/json application/xml image/svg+xml font/ttf font/otf application/wasm
</IfModule>
# ── Correct MIME types (fixes blank page) ─────────────
<IfModule mod_mime.c>
AddType application/wasm .wasm
AddType application/javascript .js
AddType application/manifest+json .webmanifest
</IfModule>
# ── Disable LiteSpeed cache for entry files ───────────
<IfModule LiteSpeed>
<FilesMatch "^(index\.html|flutter_service_worker\.js|flutter_bootstrap\.js|manifest\.json)$">
CacheDisable public
</FilesMatch>
</IfModule>
ErrorDocument 404 /index.html
This project already ships with this file at
admin_panel/web/.htaccess and
customer_web/web/.htaccess — any build will carry it into
build/web/ automatically.
2. Build the release bundle
flutter clean
flutter pub get
flutter build web --release
3. Upload to Hostinger
- Open hPanel → File Manager, or connect via FTP.
- Navigate to the target folder:
- Main domain: public_html/
- Subdomain (e.g. admin.yourdomain.com):
domains/admin.yourdomain.com/public_html/
- Delete everything currently in that folder (including any old
flutter_service_worker.js, main.dart.js,
and assets/).
- Upload the contents of build/web/
(not the folder itself) including the hidden .htaccess.
💡 Make hidden files visible in Hostinger File Manager
By default the File Manager hides dotfiles. Click the gear icon (settings)
in the top-right of File Manager and enable "Show hidden files" so you can
see and upload .htaccess.
4. Purge Hostinger's LiteSpeed cache
- In hPanel, go to Advanced → Cache Manager
(or LiteSpeed Cache).
- Click Purge All.
- If you use Cloudflare in front of Hostinger, also purge Cloudflare cache
(Dashboard → Caching → Purge Everything).
5. Force-refresh your browser
Even with the new .htaccess, any visitor who already loaded the old
service worker still has it installed. The first visit after your upload may still show the old
version. To verify immediately:
- Open DevTools (F12) → Application tab
→ Service Workers → click Unregister.
- Under Storage in the same tab, click Clear site data.
- Hard reload: Ctrl + Shift + R (Windows / Linux) or
Cmd + Shift + R (macOS).
6. Verify the deploy
- Open https://yourdomain.com/ads-listing directly
— it should load the page (not a 404). If you get 404, the
.htaccess didn't make it to the server or
mod_rewrite is disabled.
- Open DevTools → Network → hard reload. The response header for
index.html should include
Cache-Control: no-store, no-cache, must-revalidate.
If you see max-age=31536000 instead, the
.htaccess is not active.
Common Hostinger-specific issues
Blank white page after upload
- Check the browser console (F12). If you see
MIME type ('text/html') is not executable errors for
.js or .wasm files, the MIME type
section of .htaccess is missing or overridden — re-upload
the .htaccess.
- Make sure all files from build/web/ were
uploaded, including the assets/,
canvaskit/, and icons/ folders.
Direct URLs (e.g. /ad-listing-detail) return 404
- Your .htaccess is missing or
mod_rewrite is disabled. Confirm the file is in the same folder
as index.html. If it still fails, open a support ticket with
Hostinger and ask them to enable mod_rewrite and
AllowOverride All for your domain.
Old version keeps loading
- Purge LiteSpeed cache (step 4 above).
- Unregister the service worker + clear site data (step 5 above).
- If the problem persists for end users, bump the version in
pubspec.yaml
(e.g. version: 1.0.0+2) and rebuild — Flutter uses the
version to invalidate the service worker cache.
eSellify ships with three optional features that are configured entirely from the
Admin Panel — no code changes required. Each is described below.
Monetize the apps with Google ads. The mobile customer app (Android & iOS) uses
Google AdMob for banner, interstitial and native ads, while the customer web build uses
Google Ad Manager (GPT) for banner slots. Everything is configured from one admin screen.
1. Get Your Ad IDs
- AdMob (mobile): create an app in the AdMob console and create ad units to obtain the
App ID (ca-app-pub-xxxxx~xxxxx) and ad-unit IDs
(ca-app-pub-xxxxx/xxxxx) for banner, interstitial and native.
- Ad Manager / AdX (web): from Google Ad Manager note your Network Code and create an ad unit
to get the Banner Slot ID (/networkCode/unitName).
2. Configure in the Admin Panel
- Open Admin Panel → Settings → Google Ads.
- Choose the Ad Network — Google AdMob or
Google AdX (Ad Manager).
- Under Mobile Ads: toggle it on and paste the AdMob Android App ID, iOS App ID, and the
Banner / Interstitial / Native ad-unit IDs.
- Under Web Ads: toggle it on and paste the Ad Manager Network Code and Web Banner Slot
ID.
- Click Save.
Per-platform toggles:
Mobile and Web each have their own on/off switch, so you can run ads on the website while keeping the
app ad-free (or vice-versa). If a switch is off, no ads load on that platform.
Note:
- For the mobile app the AdMob App ID must also be present in the native config
(AndroidManifest.xml and iOS Info.plist)
as required by Google — rebuild the app after changing it.
- On the web, if Google doesn’t serve a creative the banner area automatically collapses, so
empty ad slots never leave a blank strip on the page.
- New AdMob/Ad Manager accounts can take time to start serving live ads — use test IDs during
development.
When enabled, sellers can auto-fill an ad from its photos. The app sends the uploaded images (plus an
optional product-name hint) to OpenAI Vision, which generates the
title, description, suggested price, best-fit category and any
custom-field values for that category.
1. Get an OpenAI API Key
- Sign in at platform.openai.com.
- Go to API Keys and click "Create new secret key".
- Copy the key (starts with sk-) — you won’t be able to view it
again.
- Make sure your OpenAI account has billing enabled / available credit, since Vision requests are
billed per use.
2. Configure in the Admin Panel
- Open Admin Panel → Settings → OpenAI Settings.
- Turn on Enable AI Auto-Generation.
- Paste your OpenAI API Key.
- Pick a Model — gpt-4o-mini (fastest / cheapest),
gpt-4o, or gpt-4-turbo.
- (Optional) provide a Custom Prompt to override the default generation instructions.
- Click Save.
3. How Sellers Use It
- On the “Post Your Ad” screen (customer app, customer web, and the admin’s Create
Advertisement dialog) a "Generate with AI from photos" button appears once a photo is
uploaded.
- Tapping it fills in the title, description, price and category-specific fields. If the chosen
category doesn’t match the photo, the AI re-classifies it automatically.
Security note:
The OpenAI key is stored in your Firestore settings and read by the apps. Keep the feature disabled if
you don’t intend to use it, and monitor usage in your OpenAI dashboard. The key field is masked
in the admin UI when running in demo mode.
Safety Tips are short buyer-safety reminders shown in a bottom sheet when a user taps Chat or
Make an offer on a listing (similar to OLX). The list is fully managed from the admin
panel — no app update needed.
Manage the Tips
- Open Admin Panel → Settings → Safety Tips.
- Click "+ Add Safety Tip" to create a tip (e.g. “Never hand over money or products
upfront.”).
- Use the sort order to control the order tips appear in, and the active
toggle to show/hide a tip without deleting it.
- Edit or delete tips at any time — changes appear in the apps immediately.
Note:
If no active tips are configured, the safety bottom sheet is skipped automatically and the buyer goes
straight to chat / offer, so the feature never blocks the contact flow.
Here are solutions to common issues you might encounter during setup.
Flutter Issues
"flutter" is not recognized as a command
- Ensure Flutter is added to your system PATH. Restart your terminal after making changes.
- On Windows, verify via System Properties > Environment Variables.
- On macOS/Linux, check your .zshrc or .bashrc
file.
flutter doctor shows issues
- Run flutter doctor -v for detailed output.
- Install missing components as indicated by the output.
- Accept Android licenses with: flutter doctor --android-licenses
Firebase Issues
Firebase CLI not found
- Install globally: npm install -g firebase-tools
- Verify with: firebase --version
Permission denied during firebase deploy
- Ensure you're logged in: firebase login
- Check that you have Editor or Owner role in the Firebase project.
Cloud Functions Issues
Error: "Your project must be on the Blaze (pay-as-you-go) plan"
- Cloud Functions require the Blaze plan. Upgrade in Firebase Console > your project >
Upgrade button.
- The Blaze plan includes a generous free tier. You won't be charged for typical usage.
Error: "Cannot set CPU on gen 1 functions"
- This happens when deploying v2 functions over previously deployed v1 functions with the same name.
- Delete the old v1 functions from the Firebase Console > Functions tab, then redeploy.
Deployment fails with API errors
- Ensure the required APIs are enabled in
Google Cloud Console:
Cloud Functions, Cloud Build, Artifact Registry, Cloud Run, Eventarc.
- The Firebase CLI usually enables them automatically, but permission issues may require manual
activation.
Node version mismatch error
- The "node" version in functions/package.json
must match your local Node.js version.
- Check with node --version and update package.json accordingly.
Google Maps Issues
Map shows grey/blank
- Verify your API key is correct and not restricted to a different app.
- Ensure the required Google Maps APIs are enabled in the Google Cloud Console.
- Check that billing is enabled on your Google Cloud project.
Build Issues
Build fails with Gradle errors
- Run flutter clean followed by flutter pub get.
- Check that your minSdkVersion in android/app/build.gradle is compatible with all dependencies.
iOS build fails
- Run cd ios && pod install && cd .. to reinstall iOS dependencies.
- Open ios/Runner.xcworkspace in Xcode and check for signing/provisioning
issues.
Q: Do I need a Mac to build the iOS app?
Yes. Xcode is required for building iOS apps, and Xcode only runs on macOS. You can develop and test the
Android and Web versions on Windows or Linux.
Q: Which Firebase plan do I need?
The Blaze plan (pay-as-you-go) is recommended. phone authentication, and some other
features are not available on the free Spark plan. The Blaze plan still includes a free usage tier.
Q: Can I use my own backend instead of Firebase?
eSellify is designed to work with Firebase. Using a different backend would require significant
modifications to the codebase.
Q: How do I update the app after making changes?
After making code changes, rebuild the app using the appropriate build commands (flutter build apk, flutter build web, etc.) and
redeploy.
Q: The app crashes on startup. What should I check?
- Ensure google-services.json (Android) and GoogleService-Info.plist (iOS) are correctly placed.
- Verify Firebase is properly initialized in main.dart.
- Check the console logs for error messages using flutter run --verbose.
Q: Which payment gateways are supported?
eSellify supports Stripe, Razorpay, PayPal,
Flutterwave, and Cash on Delivery (COD). You can configure your
preferred gateway in the Admin Panel settings.
Q: How do I contact support?
Version 1.3
23 May 2026
Latest
- Send Test Email — added functionality for SMTP/email configuration testing.
- Ad Details screen — created a dedicated Ad Details screen in the Admin Panel.
- Job Category flow — implemented the complete Job Category flow, including job applications visibility in the customer app.
- Job Applications in Admin — added functionality to view users' job applications in the Admin Panel.
- Dependency upgrades — upgraded project dependencies/packages to the latest compatible versions.
- Bug fixes & stability — fixed minor bugs and improved overall app performance and stability.
Version 1.2
12 May 2026
- Google AdMob & AdX integration — banner, interstitial and native ads on mobile, GPT banner on web, configured from a new admin panel.
- Safety Tips feature — admin-managed buyer-safety reminders shown in a bottom sheet before contacting a seller.
- AI-generated ad content — OpenAI Vision auto-fills title, description, price, category and custom fields from uploaded product photos.
Version 1.1
18 April 2026
- Completed full conversion of the mobile application into a high-performance web version.
- Introduced web-based paginated ad listings with precise distance-based filtering.
- Upgraded to Flutter 3.41.6 for improved compatibility.
- Updated all project dependencies to their latest stable versions.
- Refined the web platform with critical bug fixes and enhanced navigation performance.
- Optimized the web experience with proximity-sorted ads and smooth paginated browsing.
Version 1.0
11 April 2026