backup
286
PLAY_STORE_CHECKLIST.md
Normal file
@ -0,0 +1,286 @@
|
|||||||
|
# Google Play Store Pre-Upload Checklist
|
||||||
|
|
||||||
|
Use this checklist before uploading to Google Play Store to ensure everything is ready.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📋 Phase 1: Assets & Content
|
||||||
|
|
||||||
|
### Icons
|
||||||
|
- [x] ✅ PNG icons generated (72, 96, 128, 144, 152, 192, 384, 512)
|
||||||
|
- [x] ✅ Maskable icon created (512x512 with safe zone)
|
||||||
|
- [x] ✅ Adaptive icon layers (foreground + background)
|
||||||
|
- [x] ✅ Icons added to manifest
|
||||||
|
|
||||||
|
**Location:** `pwa/public/icons/`
|
||||||
|
|
||||||
|
### Screenshots
|
||||||
|
- [ ] ⏳ Captured minimum 2 screenshots (recommended 4-8)
|
||||||
|
- [ ] ⏳ Screenshots are 1080x2340 (portrait)
|
||||||
|
- [ ] ⏳ Screenshots show actual app content
|
||||||
|
- [ ] ⏳ Screenshots saved as PNG
|
||||||
|
- [ ] ⏳ Screenshots named `screenshot-1.png`, `screenshot-2.png`, etc.
|
||||||
|
|
||||||
|
**Location:** `pwa/public/screenshots/`
|
||||||
|
**Guide:** See `pwa/public/screenshots/README.md`
|
||||||
|
|
||||||
|
### Feature Graphic
|
||||||
|
- [x] ✅ Created 1024x500 banner
|
||||||
|
- [x] ✅ No transparency (solid background)
|
||||||
|
- [x] ✅ Saved as PNG
|
||||||
|
|
||||||
|
**Location:** `pwa/public/assets/feature-graphic.png`
|
||||||
|
|
||||||
|
### Privacy Policy
|
||||||
|
- [x] ✅ Privacy policy written
|
||||||
|
- [x] ✅ Route added to PWA (`/privacy-policy`)
|
||||||
|
- [x] ✅ Accessible at `https://app.placebo.mk/privacy-policy`
|
||||||
|
- [x] ✅ Covers data collection (PostHog, cache, etc.)
|
||||||
|
- [x] ✅ GDPR compliant
|
||||||
|
|
||||||
|
**URL:** https://app.placebo.mk/privacy-policy
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🔧 Phase 2: Technical Setup
|
||||||
|
|
||||||
|
### PWA Configuration
|
||||||
|
- [x] ✅ Manifest updated with PNG icons
|
||||||
|
- [x] ✅ Categories added (`news`, `entertainment`)
|
||||||
|
- [x] ✅ Orientation set to `portrait-primary`
|
||||||
|
- [x] ✅ Theme colors configured
|
||||||
|
- [x] ✅ Service worker working
|
||||||
|
- [x] ✅ Offline functionality tested
|
||||||
|
|
||||||
|
**File:** `pwa/vite.config.ts`
|
||||||
|
|
||||||
|
### Digital Asset Links
|
||||||
|
- [x] ✅ `assetlinks.json` template created
|
||||||
|
- [ ] ⏳ SHA256 fingerprint updated (after PWABuilder)
|
||||||
|
- [x] ✅ Nginx configured to serve `.well-known/`
|
||||||
|
- [ ] ⏳ File accessible at `https://app.placebo.mk/.well-known/assetlinks.json`
|
||||||
|
- [ ] ⏳ Validated with Google's tool
|
||||||
|
|
||||||
|
**File:** `pwa/public/.well-known/assetlinks.json`
|
||||||
|
**Validator:** https://digitalassetlinks.googleapis.com/v1/statements:list?source.web.site=https://app.placebo.mk
|
||||||
|
|
||||||
|
### Build & Deployment
|
||||||
|
- [x] ✅ TypeScript check passes
|
||||||
|
- [x] ✅ ESLint passes
|
||||||
|
- [x] ✅ Production build successful
|
||||||
|
- [ ] ⏳ Updated PWA deployed to `https://app.placebo.mk`
|
||||||
|
- [ ] ⏳ PWA accessible and working
|
||||||
|
|
||||||
|
**Commands:**
|
||||||
|
```bash
|
||||||
|
cd pwa
|
||||||
|
npm run type-check
|
||||||
|
npm run lint
|
||||||
|
npm run build
|
||||||
|
# Deploy to Coolify
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📱 Phase 3: Android App Generation
|
||||||
|
|
||||||
|
### PWABuilder Setup
|
||||||
|
- [ ] ⏳ PWA URL entered: `https://app.placebo.mk`
|
||||||
|
- [ ] ⏳ PWA score checked (should be high)
|
||||||
|
- [ ] ⏳ Package configured:
|
||||||
|
- App name: `Placebo.mk`
|
||||||
|
- Package ID: `mk.placebo.app`
|
||||||
|
- Launch URL: `https://app.placebo.mk/`
|
||||||
|
- Theme color: `#000000`
|
||||||
|
- Background: `#ffffff`
|
||||||
|
- Orientation: `portrait`
|
||||||
|
|
||||||
|
### Signing Key
|
||||||
|
- [ ] ⏳ Signing method chosen (Cloud or Own)
|
||||||
|
- [ ] ⏳ Signing key generated
|
||||||
|
- [ ] ⏳ SHA256 fingerprint copied
|
||||||
|
- [ ] ⏳ Signing details saved securely
|
||||||
|
|
||||||
|
⚠️ **IMPORTANT:** Keep signing key details secure! You'll need them for updates.
|
||||||
|
|
||||||
|
### App Package
|
||||||
|
- [ ] ⏳ AAB file downloaded
|
||||||
|
- [ ] ⏳ Test APK downloaded (optional)
|
||||||
|
- [ ] ⏳ SHA256 fingerprint added to `assetlinks.json`
|
||||||
|
- [ ] ⏳ Updated PWA redeployed
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🧪 Phase 4: Testing (Optional but Recommended)
|
||||||
|
|
||||||
|
### Local Testing
|
||||||
|
- [ ] ⏳ APK installed on device
|
||||||
|
- [ ] ⏳ App opens without browser UI (TWA verified)
|
||||||
|
- [ ] ⏳ Navigation works correctly
|
||||||
|
- [ ] ⏳ Offline mode works
|
||||||
|
- [ ] ⏳ Analytics (PostHog) fires
|
||||||
|
- [ ] ⏳ No crashes or errors
|
||||||
|
|
||||||
|
### PWA Testing
|
||||||
|
- [ ] ⏳ Manifest validates: https://manifest-validator.appspot.com/
|
||||||
|
- [ ] ⏳ Service worker registers
|
||||||
|
- [ ] ⏳ Icons display correctly
|
||||||
|
- [ ] ⏳ Privacy policy loads
|
||||||
|
- [ ] ⏳ All routes work
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🏪 Phase 5: Google Play Console Setup
|
||||||
|
|
||||||
|
### Account & App
|
||||||
|
- [x] ✅ Google Play Developer account active
|
||||||
|
- [ ] ⏳ App created in Play Console
|
||||||
|
- [ ] ⏳ App name set: `Placebo.mk`
|
||||||
|
- [ ] ⏳ Default language: Macedonian (mk-MK)
|
||||||
|
- [ ] ⏳ Free app selected
|
||||||
|
|
||||||
|
### Store Listing
|
||||||
|
- [ ] ⏳ Short description written (max 80 chars)
|
||||||
|
- [ ] ⏳ Full description written (max 4000 chars)
|
||||||
|
- [ ] ⏳ Screenshots uploaded (2-8 images)
|
||||||
|
- [ ] ⏳ Feature graphic uploaded
|
||||||
|
- [ ] ⏳ App icon uploaded (512x512)
|
||||||
|
- [ ] ⏳ Category selected: News & Magazines
|
||||||
|
- [ ] ⏳ Contact email: `privacy@placebo.mk`
|
||||||
|
- [ ] ⏳ Website: `https://placebo.mk`
|
||||||
|
- [ ] ⏳ Privacy policy URL: `https://app.placebo.mk/privacy-policy`
|
||||||
|
|
||||||
|
### Content Rating
|
||||||
|
- [ ] ⏳ Content rating questionnaire completed
|
||||||
|
- [ ] ⏳ Category: News & Reference
|
||||||
|
- [ ] ⏳ Questions answered honestly
|
||||||
|
- [ ] ⏳ Ratings applied
|
||||||
|
|
||||||
|
### Target Audience
|
||||||
|
- [ ] ⏳ Target age selected (13+ or 18+)
|
||||||
|
- [ ] ⏳ Ads declaration completed
|
||||||
|
- [ ] ⏳ Target audience declaration submitted
|
||||||
|
|
||||||
|
### Countries & Pricing
|
||||||
|
- [ ] ⏳ Countries selected (North Macedonia + others)
|
||||||
|
- [ ] ⏳ Pricing set to Free
|
||||||
|
- [ ] ⏳ Distribution settings confirmed
|
||||||
|
|
||||||
|
### App Release
|
||||||
|
- [ ] ⏳ AAB file uploaded
|
||||||
|
- [ ] ⏳ Upload processed successfully
|
||||||
|
- [ ] ⏳ Supported devices shown
|
||||||
|
- [ ] ⏳ Release notes added (Macedonian + English)
|
||||||
|
- [ ] ⏳ Release reviewed
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## ✅ Final Checks Before Submission
|
||||||
|
|
||||||
|
### Critical Items
|
||||||
|
- [ ] ⏳ All Play Console sections marked complete (green checkmarks)
|
||||||
|
- [ ] ⏳ No errors or warnings in Play Console
|
||||||
|
- [ ] ⏳ Privacy policy accessible
|
||||||
|
- [ ] ⏳ Digital Asset Links verified
|
||||||
|
- [ ] ⏳ PWA live at `https://app.placebo.mk`
|
||||||
|
- [ ] ⏳ Screenshots captured and uploaded
|
||||||
|
- [ ] ⏳ Feature graphic uploaded
|
||||||
|
- [ ] ⏳ Content rating assigned
|
||||||
|
- [ ] ⏳ AAB uploaded successfully
|
||||||
|
|
||||||
|
### Nice to Have
|
||||||
|
- [ ] ⏳ Test APK installed and working
|
||||||
|
- [ ] ⏳ App preview video (optional)
|
||||||
|
- [ ] ⏳ Promo graphics (optional)
|
||||||
|
- [ ] ⏳ Social media announcement prepared
|
||||||
|
- [ ] ⏳ Website updated with app link
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🚀 Submission
|
||||||
|
|
||||||
|
When all items above are complete:
|
||||||
|
|
||||||
|
1. [ ] ⏳ Click "Review release" in Play Console
|
||||||
|
2. [ ] ⏳ Fix any issues highlighted
|
||||||
|
3. [ ] ⏳ Click "Start rollout to Production"
|
||||||
|
4. [ ] ⏳ Confirm submission
|
||||||
|
5. [ ] ⏳ Wait for Google's review (1-7 days)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📊 Post-Submission
|
||||||
|
|
||||||
|
After submitting:
|
||||||
|
|
||||||
|
- [ ] ⏳ Monitor Play Console for review status
|
||||||
|
- [ ] ⏳ Check email for Google notifications
|
||||||
|
- [ ] ⏳ Prepare announcement content
|
||||||
|
- [ ] ⏳ Set up monitoring for crashes/errors
|
||||||
|
|
||||||
|
When approved:
|
||||||
|
|
||||||
|
- [ ] ⏳ Announce on social media
|
||||||
|
- [ ] ⏳ Update website with Play Store badge
|
||||||
|
- [ ] ⏳ Email users about app availability
|
||||||
|
- [ ] ⏳ Monitor reviews and respond
|
||||||
|
- [ ] ⏳ Track analytics and downloads
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 🆘 If Something Goes Wrong
|
||||||
|
|
||||||
|
### Common Issues:
|
||||||
|
|
||||||
|
**Upload fails:**
|
||||||
|
- Check AAB file size (max 150MB)
|
||||||
|
- Verify signing key
|
||||||
|
- Try uploading again
|
||||||
|
|
||||||
|
**TWA doesn't work:**
|
||||||
|
- Verify SHA256 fingerprint
|
||||||
|
- Check assetlinks.json URL
|
||||||
|
- Wait 5-10 minutes for cache
|
||||||
|
|
||||||
|
**App rejected:**
|
||||||
|
- Read rejection reason carefully
|
||||||
|
- Fix issues
|
||||||
|
- Resubmit
|
||||||
|
|
||||||
|
**Privacy policy error:**
|
||||||
|
- Ensure URL is accessible
|
||||||
|
- Check HTTPS is working
|
||||||
|
- Verify content is complete
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📁 Important File Locations
|
||||||
|
|
||||||
|
| Item | Location |
|
||||||
|
|------|----------|
|
||||||
|
| Icons | `pwa/public/icons/icon-*.png` |
|
||||||
|
| Maskable Icon | `pwa/public/icons/icon-512-maskable.png` |
|
||||||
|
| Screenshots | `pwa/public/screenshots/` |
|
||||||
|
| Feature Graphic | `pwa/public/assets/feature-graphic.png` |
|
||||||
|
| Privacy Policy | `pwa/src/components/routes/PrivacyPolicyComponent.tsx` |
|
||||||
|
| Asset Links | `pwa/public/.well-known/assetlinks.json` |
|
||||||
|
| Nginx Config | `pwa/nginx.conf` |
|
||||||
|
| Manifest Config | `pwa/vite.config.ts` |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 📚 Resources
|
||||||
|
|
||||||
|
- **Full Guide:** See `PLAY_STORE_GUIDE.md` in project root
|
||||||
|
- **Screenshots Guide:** See `pwa/public/screenshots/README.md`
|
||||||
|
- **Asset Links Guide:** See `pwa/public/.well-known/README.md`
|
||||||
|
- **PWABuilder:** https://www.pwabuilder.com/
|
||||||
|
- **Play Console:** https://play.google.com/console
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
**Current Status:** Ready for screenshot capture and PWABuilder packaging
|
||||||
|
|
||||||
|
**Next Action:** Capture screenshots from deployed PWA
|
||||||
|
|
||||||
|
Good luck! 🎉
|
||||||
490
PLAY_STORE_GUIDE.md
Normal file
@ -0,0 +1,490 @@
|
|||||||
|
# Google Play Store Publishing Guide
|
||||||
|
|
||||||
|
Complete step-by-step guide for publishing Placebo.mk PWA to Google Play Store using PWABuilder.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Prerequisites Checklist
|
||||||
|
|
||||||
|
Before starting, ensure you have:
|
||||||
|
|
||||||
|
- [x] ✅ PWA deployed and accessible at `https://app.placebo.mk`
|
||||||
|
- [x] ✅ Privacy Policy accessible at `https://app.placebo.mk/privacy-policy`
|
||||||
|
- [x] ✅ PNG icons generated (72px - 512px)
|
||||||
|
- [x] ✅ Maskable icon (512x512)
|
||||||
|
- [x] ✅ Feature graphic (1024x500) at `pwa/public/assets/feature-graphic.png`
|
||||||
|
- [ ] ⏳ Screenshots captured (see `pwa/public/screenshots/README.md`)
|
||||||
|
- [x] ✅ Google Play Developer account ($25 one-time fee)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 1: Capture Screenshots
|
||||||
|
|
||||||
|
**Time estimate:** 15-30 minutes
|
||||||
|
|
||||||
|
### Instructions:
|
||||||
|
|
||||||
|
1. Open Chrome browser
|
||||||
|
2. Navigate to `https://app.placebo.mk`
|
||||||
|
3. Press `F12` → Click device toolbar (or `Ctrl+Shift+M`)
|
||||||
|
4. Select device: **Pixel 5** (1080 x 2340)
|
||||||
|
5. Capture these screens:
|
||||||
|
- Homepage (hero article + latest articles)
|
||||||
|
- Article detail page
|
||||||
|
- Archive page
|
||||||
|
- Live blogs page
|
||||||
|
- Category page (Sport/Art/Science)
|
||||||
|
- Any other unique feature
|
||||||
|
|
||||||
|
6. Click three dots in device toolbar → "Capture screenshot"
|
||||||
|
7. Save as `screenshot-1.png`, `screenshot-2.png`, etc.
|
||||||
|
8. Place in `pwa/public/screenshots/`
|
||||||
|
|
||||||
|
**Requirements:**
|
||||||
|
- Minimum 2 screenshots
|
||||||
|
- Recommended 4-8 screenshots
|
||||||
|
- Format: PNG
|
||||||
|
- Portrait orientation (1080x2340)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 2: Generate Android App with PWABuilder
|
||||||
|
|
||||||
|
**Time estimate:** 20-30 minutes
|
||||||
|
|
||||||
|
### Step 1: Access PWABuilder
|
||||||
|
|
||||||
|
1. Go to https://www.pwabuilder.com/
|
||||||
|
2. Enter your PWA URL: `https://app.placebo.mk`
|
||||||
|
3. Click "Start"
|
||||||
|
|
||||||
|
### Step 2: Review PWA Score
|
||||||
|
|
||||||
|
PWABuilder will analyze your PWA and show a score. You should see:
|
||||||
|
- ✅ Manifest detected
|
||||||
|
- ✅ Service Worker registered
|
||||||
|
- ✅ HTTPS enabled
|
||||||
|
- ✅ Icons present
|
||||||
|
|
||||||
|
If any checks fail, fix them before proceeding.
|
||||||
|
|
||||||
|
### Step 3: Package for Android
|
||||||
|
|
||||||
|
1. Click "Package For Stores"
|
||||||
|
2. Select **Android** platform
|
||||||
|
3. Click "Generate Package"
|
||||||
|
|
||||||
|
### Step 4: Configure Android Settings
|
||||||
|
|
||||||
|
Fill in the following:
|
||||||
|
|
||||||
|
| Field | Value |
|
||||||
|
|-------|-------|
|
||||||
|
| **App Name** | `Placebo.mk` |
|
||||||
|
| **Package ID** | `mk.placebo.app` |
|
||||||
|
| **Launch URL** | `https://app.placebo.mk/` |
|
||||||
|
| **Display Mode** | `standalone` |
|
||||||
|
| **Theme Color** | `#000000` |
|
||||||
|
| **Background Color** | `#ffffff` |
|
||||||
|
| **Orientation** | `portrait` |
|
||||||
|
| **Icon URL** | `https://app.placebo.mk/icons/icon-512.png` |
|
||||||
|
| **Maskable Icon URL** | `https://app.placebo.mk/icons/icon-512-maskable.png` |
|
||||||
|
| **Shortcuts** | Leave empty (optional) |
|
||||||
|
| **Splash Screen** | Auto-generated from icon |
|
||||||
|
|
||||||
|
### Step 5: Signing Options
|
||||||
|
|
||||||
|
Choose **one** of these options:
|
||||||
|
|
||||||
|
#### Option A: Use PWABuilder Cloud Signing (Recommended)
|
||||||
|
|
||||||
|
✅ **Pros:** Easy, no setup, signing key managed for you
|
||||||
|
❌ **Cons:** Key stored by PWABuilder (trusted service)
|
||||||
|
|
||||||
|
1. Select "Use new signing key"
|
||||||
|
2. PWABuilder will generate and store your key
|
||||||
|
3. Download the signing details (keep secure!)
|
||||||
|
|
||||||
|
#### Option B: Use Your Own Signing Key
|
||||||
|
|
||||||
|
✅ **Pros:** Full control over signing key
|
||||||
|
❌ **Cons:** More complex, must manage keystore securely
|
||||||
|
|
||||||
|
1. Generate keystore locally:
|
||||||
|
```bash
|
||||||
|
keytool -genkey -v -keystore placebo-release.keystore \
|
||||||
|
-alias placebo-key -keyalg RSA -keysize 2048 -validity 10000
|
||||||
|
```
|
||||||
|
|
||||||
|
2. Upload keystore to PWABuilder
|
||||||
|
3. Enter keystore password and alias
|
||||||
|
|
||||||
|
### Step 6: Generate Package
|
||||||
|
|
||||||
|
1. Click "Generate Package"
|
||||||
|
2. Wait 2-5 minutes for build to complete
|
||||||
|
3. Download the generated package (AAB or APK)
|
||||||
|
|
||||||
|
### Step 7: Extract SHA256 Fingerprint
|
||||||
|
|
||||||
|
PWABuilder will show your SHA256 fingerprint. It looks like:
|
||||||
|
```
|
||||||
|
14:6D:E9:83:C5:73:06:50:D8:EE:B9:95:2F:34:FC:64:16:A0:83:42:E3:6D:3A:AE:4E:9F:5F:E8:E3:91:A0:7E
|
||||||
|
```
|
||||||
|
|
||||||
|
**IMPORTANT:** Copy this fingerprint - you'll need it for Digital Asset Links.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 3: Update Digital Asset Links
|
||||||
|
|
||||||
|
**Time estimate:** 5-10 minutes
|
||||||
|
|
||||||
|
### Step 1: Update assetlinks.json
|
||||||
|
|
||||||
|
1. Open `pwa/public/.well-known/assetlinks.json`
|
||||||
|
2. Replace `PLACEHOLDER_SHA256_FINGERPRINT_FROM_PWABUILDER` with your actual fingerprint
|
||||||
|
3. Save the file
|
||||||
|
|
||||||
|
Example:
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"relation": ["delegate_permission/common.handle_all_urls"],
|
||||||
|
"target": {
|
||||||
|
"namespace": "android_app",
|
||||||
|
"package_name": "mk.placebo.app",
|
||||||
|
"sha256_cert_fingerprints": [
|
||||||
|
"14:6D:E9:83:C5:73:06:50:D8:EE:B9:95:2F:34:FC:64:16:A0:83:42:E3:6D:3A:AE:4E:9F:5F:E8:E3:91:A0:7E"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Step 2: Deploy Updated PWA
|
||||||
|
|
||||||
|
Rebuild and deploy your PWA with the updated assetlinks.json:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd pwa
|
||||||
|
npm run build
|
||||||
|
# Deploy to Coolify or your hosting platform
|
||||||
|
```
|
||||||
|
|
||||||
|
### Step 3: Verify Deployment
|
||||||
|
|
||||||
|
Check that the file is accessible:
|
||||||
|
```bash
|
||||||
|
curl https://app.placebo.mk/.well-known/assetlinks.json
|
||||||
|
```
|
||||||
|
|
||||||
|
Validate with Google:
|
||||||
|
```bash
|
||||||
|
curl "https://digitalassetlinks.googleapis.com/v1/statements:list?source.web.site=https://app.placebo.mk"
|
||||||
|
```
|
||||||
|
|
||||||
|
You should see your statement without errors.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 4: Test Locally (Optional but Recommended)
|
||||||
|
|
||||||
|
**Time estimate:** 15-20 minutes
|
||||||
|
|
||||||
|
### Step 1: Install APK
|
||||||
|
|
||||||
|
PWABuilder provides a test APK. Install it on your Android device:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
adb install -r placebo-mk.apk
|
||||||
|
```
|
||||||
|
|
||||||
|
Or email the APK to yourself and install manually.
|
||||||
|
|
||||||
|
### Step 2: Test Functionality
|
||||||
|
|
||||||
|
Verify:
|
||||||
|
- ✅ App opens without browser UI (TWA verification)
|
||||||
|
- ✅ Icons display correctly
|
||||||
|
- ✅ Offline mode works
|
||||||
|
- ✅ Navigation works
|
||||||
|
- ✅ PostHog analytics fires
|
||||||
|
- ✅ Deep links work (if applicable)
|
||||||
|
|
||||||
|
### Step 3: Debug Issues
|
||||||
|
|
||||||
|
If TWA doesn't work (shows browser UI):
|
||||||
|
- Check assetlinks.json is accessible
|
||||||
|
- Verify SHA256 fingerprint matches
|
||||||
|
- Ensure package name is correct
|
||||||
|
- Wait 5-10 minutes for DNS/CDN propagation
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 5: Upload to Google Play Console
|
||||||
|
|
||||||
|
**Time estimate:** 30-60 minutes
|
||||||
|
|
||||||
|
### Step 1: Create App in Play Console
|
||||||
|
|
||||||
|
1. Go to https://play.google.com/console
|
||||||
|
2. Click "Create app"
|
||||||
|
3. Fill in details:
|
||||||
|
- **App name:** Placebo.mk
|
||||||
|
- **Default language:** Macedonian (mk-MK)
|
||||||
|
- **App or game:** App
|
||||||
|
- **Free or paid:** Free
|
||||||
|
4. Accept declarations
|
||||||
|
5. Click "Create app"
|
||||||
|
|
||||||
|
### Step 2: Complete Store Listing
|
||||||
|
|
||||||
|
Navigate to **Store presence → Main store listing**
|
||||||
|
|
||||||
|
Fill in:
|
||||||
|
|
||||||
|
**App Details:**
|
||||||
|
- **App name:** Placebo.mk
|
||||||
|
- **Short description:** (max 80 chars)
|
||||||
|
```
|
||||||
|
Сатирични вести од Македонија - непристојно искрено и секогаш без филтер
|
||||||
|
```
|
||||||
|
- **Full description:** (max 4000 chars)
|
||||||
|
```
|
||||||
|
Placebo.mk е платформа за сатирични вести и коментари за локални и глобални настани во Македонија.
|
||||||
|
|
||||||
|
🎯 Што нудиме:
|
||||||
|
• Свежи сатирични вести за тековни настани
|
||||||
|
• Непристоен и директен коментар без филтер
|
||||||
|
• Live блогови за разбивачки вести во реално време
|
||||||
|
• Offline пристап до сите статии
|
||||||
|
• Категории: Политика, Спорт, Уметност, Наука и повеќе
|
||||||
|
|
||||||
|
⚡ Карактеристики:
|
||||||
|
• Брзо и лесно читање на статии
|
||||||
|
• Работи offline - читајте и без интернет
|
||||||
|
• Push известувања за нови статии
|
||||||
|
• Делете статии на социјални медиуми
|
||||||
|
• Темна и светла тема
|
||||||
|
|
||||||
|
Затоа што понекогаш вистината боли повеќе од фикцијата.
|
||||||
|
|
||||||
|
Следете не на web: https://placebo.mk
|
||||||
|
```
|
||||||
|
|
||||||
|
**Graphics:**
|
||||||
|
- Upload screenshots (2-8 images from `pwa/public/screenshots/`)
|
||||||
|
- Upload feature graphic (`pwa/public/assets/feature-graphic.png`)
|
||||||
|
- Upload app icon (512x512 from `pwa/public/icons/icon-512.png`)
|
||||||
|
|
||||||
|
**Categorization:**
|
||||||
|
- **App category:** News & Magazines
|
||||||
|
- **Tags:** news, satire, macedonia, politics (optional)
|
||||||
|
|
||||||
|
**Contact Details:**
|
||||||
|
- **Email:** privacy@placebo.mk (or your support email)
|
||||||
|
- **Website:** https://placebo.mk
|
||||||
|
- **Phone:** (optional)
|
||||||
|
|
||||||
|
**Privacy Policy:**
|
||||||
|
- **Privacy policy URL:** `https://app.placebo.mk/privacy-policy`
|
||||||
|
|
||||||
|
### Step 3: Set Up Content Rating
|
||||||
|
|
||||||
|
Navigate to **Policy → App content → Content rating**
|
||||||
|
|
||||||
|
1. Click "Start questionnaire"
|
||||||
|
2. Enter email address
|
||||||
|
3. Select category: **News & Reference**
|
||||||
|
4. Answer questions honestly:
|
||||||
|
- Does app contain violence? → (Select based on your content)
|
||||||
|
- Sexual content? → (Select based on your content)
|
||||||
|
- Language? → (Select based on your content)
|
||||||
|
- Drugs/alcohol references? → (Select based on your content)
|
||||||
|
5. Submit questionnaire
|
||||||
|
6. Apply ratings
|
||||||
|
|
||||||
|
### Step 4: Configure Target Audience
|
||||||
|
|
||||||
|
Navigate to **Policy → App content → Target audience and content**
|
||||||
|
|
||||||
|
1. **Target age:** 13+ (or 18+ if mature satire)
|
||||||
|
2. **App includes ads:** No (unless you add ads later)
|
||||||
|
3. Complete declaration
|
||||||
|
|
||||||
|
### Step 5: Select Countries
|
||||||
|
|
||||||
|
Navigate to **Release → Production → Countries/Regions**
|
||||||
|
|
||||||
|
1. Add countries:
|
||||||
|
- ✅ North Macedonia (primary)
|
||||||
|
- ✅ Other countries (optional - consider Albania, Serbia, Bulgaria, Greece for diaspora)
|
||||||
|
2. Click "Add countries/regions"
|
||||||
|
|
||||||
|
### Step 6: Upload AAB File
|
||||||
|
|
||||||
|
Navigate to **Release → Production → Create new release**
|
||||||
|
|
||||||
|
1. Click "Upload" and select the AAB file from PWABuilder
|
||||||
|
2. Wait for processing (may take 5-15 minutes)
|
||||||
|
3. Google Play will show:
|
||||||
|
- ✅ APK size
|
||||||
|
- ✅ Supported devices
|
||||||
|
- ✅ Permissions required
|
||||||
|
4. Review and confirm
|
||||||
|
|
||||||
|
### Step 7: Add Release Notes
|
||||||
|
|
||||||
|
Add release notes for the first version:
|
||||||
|
|
||||||
|
**Macedonian:**
|
||||||
|
```
|
||||||
|
Прва верзија на Placebo.mk апликацијата!
|
||||||
|
|
||||||
|
• Читајте сатирични вести од Македонија
|
||||||
|
• Offline пристап до содржини
|
||||||
|
• Live блогови за разбивачки настани
|
||||||
|
• Брз и едноставен интерфејс
|
||||||
|
```
|
||||||
|
|
||||||
|
**English (optional):**
|
||||||
|
```
|
||||||
|
First version of Placebo.mk app!
|
||||||
|
|
||||||
|
• Read satirical news from Macedonia
|
||||||
|
• Offline access to content
|
||||||
|
• Live blogs for breaking news
|
||||||
|
• Fast and simple interface
|
||||||
|
```
|
||||||
|
|
||||||
|
### Step 8: Review and Publish
|
||||||
|
|
||||||
|
1. Click "Review release"
|
||||||
|
2. Google will check for issues:
|
||||||
|
- ✅ All required fields complete
|
||||||
|
- ✅ Content rating assigned
|
||||||
|
- ✅ Target audience set
|
||||||
|
- ✅ Privacy policy accessible
|
||||||
|
3. Fix any warnings
|
||||||
|
4. Click "Start rollout to Production"
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 6: Wait for Review
|
||||||
|
|
||||||
|
**Time estimate:** 1-7 days
|
||||||
|
|
||||||
|
### What Happens Next:
|
||||||
|
|
||||||
|
1. **Submitted:** Your app enters Google's review queue
|
||||||
|
2. **Under Review:** Google reviews your app (usually 1-3 days)
|
||||||
|
3. **Approved:** App goes live on Play Store 🎉
|
||||||
|
4. **Rejected:** Fix issues and resubmit
|
||||||
|
|
||||||
|
### Common Rejection Reasons:
|
||||||
|
|
||||||
|
- ❌ Privacy policy not accessible
|
||||||
|
- ❌ Content rating doesn't match app content
|
||||||
|
- ❌ Misleading app description
|
||||||
|
- ❌ Copyright/trademark issues
|
||||||
|
- ❌ Broken functionality
|
||||||
|
|
||||||
|
### Tracking Status:
|
||||||
|
|
||||||
|
- Check Play Console dashboard
|
||||||
|
- You'll receive email notifications for status changes
|
||||||
|
- View detailed feedback in "Policy status"
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Part 7: Post-Publication
|
||||||
|
|
||||||
|
### After Your App is Live:
|
||||||
|
|
||||||
|
1. **Share the News!**
|
||||||
|
- Announce on your website
|
||||||
|
- Share on social media
|
||||||
|
- Email your users
|
||||||
|
|
||||||
|
2. **Monitor Performance:**
|
||||||
|
- Track downloads in Play Console
|
||||||
|
- Monitor crash reports
|
||||||
|
- Review user feedback/ratings
|
||||||
|
|
||||||
|
3. **Set Up Store Listing Experiments (Optional):**
|
||||||
|
- Test different screenshots
|
||||||
|
- A/B test descriptions
|
||||||
|
- Optimize icon designs
|
||||||
|
|
||||||
|
4. **Plan Updates:**
|
||||||
|
- Regular feature updates
|
||||||
|
- Bug fixes
|
||||||
|
- New content
|
||||||
|
|
||||||
|
5. **Respond to Reviews:**
|
||||||
|
- Reply to user reviews (especially negative ones)
|
||||||
|
- Show you care about user feedback
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Troubleshooting
|
||||||
|
|
||||||
|
### PWA Score is Low
|
||||||
|
- Verify manifest.json is valid
|
||||||
|
- Check service worker is registered
|
||||||
|
- Ensure HTTPS is enabled
|
||||||
|
- Add required icons
|
||||||
|
|
||||||
|
### TWA Verification Fails
|
||||||
|
- Double-check SHA256 fingerprint
|
||||||
|
- Verify assetlinks.json is at correct URL
|
||||||
|
- Ensure package name matches exactly
|
||||||
|
- Wait for CDN cache to clear (5-10 mins)
|
||||||
|
|
||||||
|
### Upload Failed
|
||||||
|
- Check AAB file size (max 150MB)
|
||||||
|
- Verify signing key is valid
|
||||||
|
- Ensure version code is unique
|
||||||
|
- Try uploading again (sometimes glitches occur)
|
||||||
|
|
||||||
|
### App Rejected
|
||||||
|
- Read rejection reason carefully
|
||||||
|
- Fix issues listed
|
||||||
|
- Update AAB and resubmit
|
||||||
|
- Contact Google Play support if unclear
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Important Files Reference
|
||||||
|
|
||||||
|
| File | Location | Purpose |
|
||||||
|
|------|----------|---------|
|
||||||
|
| Icons (PNG) | `pwa/public/icons/icon-*.png` | App icons |
|
||||||
|
| Maskable Icon | `pwa/public/icons/icon-512-maskable.png` | Adaptive icon |
|
||||||
|
| Screenshots | `pwa/public/screenshots/` | Play Store listing |
|
||||||
|
| Feature Graphic | `pwa/public/assets/feature-graphic.png` | Store banner |
|
||||||
|
| Privacy Policy | `https://app.placebo.mk/privacy-policy` | Required legal doc |
|
||||||
|
| Asset Links | `pwa/public/.well-known/assetlinks.json` | TWA verification |
|
||||||
|
| Manifest | `https://app.placebo.mk/manifest.webmanifest` | PWA config |
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Support & Resources
|
||||||
|
|
||||||
|
- **PWABuilder Docs:** https://docs.pwabuilder.com/
|
||||||
|
- **Google Play Help:** https://support.google.com/googleplay/android-developer/
|
||||||
|
- **TWA Guide:** https://developers.google.com/web/android/trusted-web-activity
|
||||||
|
- **Digital Asset Links:** https://developers.google.com/digital-asset-links/
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## Next Steps After This Guide
|
||||||
|
|
||||||
|
1. ✅ Complete all phases
|
||||||
|
2. ✅ Deploy updated PWA with assetlinks.json
|
||||||
|
3. ✅ Capture screenshots
|
||||||
|
4. ✅ Generate Android app with PWABuilder
|
||||||
|
5. ✅ Upload to Google Play Console
|
||||||
|
6. ⏳ Wait for approval
|
||||||
|
7. 🎉 Celebrate when live!
|
||||||
|
|
||||||
|
Good luck! 🚀
|
||||||
@ -48,6 +48,15 @@ http {
|
|||||||
# Security headers for frontend
|
# Security headers for frontend
|
||||||
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' 'unsafe-eval' https://eu-assets.i.posthog.com; style-src 'self' 'unsafe-inline'; style-src-elem 'self' 'unsafe-inline' https://fonts.googleapis.com; img-src 'self' data: https:; font-src 'self' data: https://fonts.gstatic.com; connect-src 'self' https://api.placebo.mk https://cms.placebo.mk https://app.placebo.mk wss://api.placebo.mk https://eu.i.posthog.com https://eu-assets.i.posthog.com; manifest-src 'self';" always;
|
add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' 'unsafe-eval' https://eu-assets.i.posthog.com; style-src 'self' 'unsafe-inline'; style-src-elem 'self' 'unsafe-inline' https://fonts.googleapis.com; img-src 'self' data: https:; font-src 'self' data: https://fonts.gstatic.com; connect-src 'self' https://api.placebo.mk https://cms.placebo.mk https://app.placebo.mk wss://api.placebo.mk https://eu.i.posthog.com https://eu-assets.i.posthog.com; manifest-src 'self';" always;
|
||||||
|
|
||||||
|
# Digital Asset Links for Android TWA
|
||||||
|
location /.well-known/ {
|
||||||
|
default_type application/json;
|
||||||
|
add_header Content-Type application/json;
|
||||||
|
add_header Access-Control-Allow-Origin *;
|
||||||
|
expires -1;
|
||||||
|
add_header Cache-Control "no-cache, no-store, must-revalidate";
|
||||||
|
}
|
||||||
|
|
||||||
# Handle React Router
|
# Handle React Router
|
||||||
location / {
|
location / {
|
||||||
try_files $uri $uri/ /index.html;
|
try_files $uri $uri/ /index.html;
|
||||||
|
|||||||
104
pwa/public/.well-known/README.md
Normal file
@ -0,0 +1,104 @@
|
|||||||
|
# Digital Asset Links Configuration
|
||||||
|
|
||||||
|
This file enables Trusted Web Activity (TWA) verification for the Placebo.mk Android app.
|
||||||
|
|
||||||
|
## What is this?
|
||||||
|
|
||||||
|
Digital Asset Links allows your Android app to open without browser UI by proving you own both the website (`https://app.placebo.mk`) and the Android app (`mk.placebo.app`).
|
||||||
|
|
||||||
|
## Current Status
|
||||||
|
|
||||||
|
⚠️ **PLACEHOLDER** - The SHA256 fingerprint needs to be updated after PWABuilder generates your signing key.
|
||||||
|
|
||||||
|
## How to Update
|
||||||
|
|
||||||
|
### Step 1: Generate Android App with PWABuilder
|
||||||
|
|
||||||
|
1. Go to https://www.pwabuilder.com/
|
||||||
|
2. Enter your PWA URL: `https://app.placebo.mk`
|
||||||
|
3. Click "Package For Stores" → "Android"
|
||||||
|
4. Download the package
|
||||||
|
|
||||||
|
### Step 2: Get SHA256 Fingerprint
|
||||||
|
|
||||||
|
PWABuilder will provide the SHA256 fingerprint in the downloaded package. Look for:
|
||||||
|
- `assetlinks.json` file in the package
|
||||||
|
- Or in the PWABuilder dashboard under "Android Package Options"
|
||||||
|
|
||||||
|
The fingerprint looks like:
|
||||||
|
```
|
||||||
|
14:6D:E9:83:C5:73:06:50:D8:EE:B9:95:2F:34:FC:64:16:A0:83:42:E3:6D:3A:AE:4E:9F:5F:E8:E3:91:A0:7E
|
||||||
|
```
|
||||||
|
|
||||||
|
### Step 3: Update assetlinks.json
|
||||||
|
|
||||||
|
Replace `PLACEHOLDER_SHA256_FINGERPRINT_FROM_PWABUILDER` in `assetlinks.json` with your actual fingerprint:
|
||||||
|
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"relation": ["delegate_permission/common.handle_all_urls"],
|
||||||
|
"target": {
|
||||||
|
"namespace": "android_app",
|
||||||
|
"package_name": "mk.placebo.app",
|
||||||
|
"sha256_cert_fingerprints": [
|
||||||
|
"14:6D:E9:83:C5:73:06:50:D8:EE:B9:95:2F:34:FC:64:16:A0:83:42:E3:6D:3A:AE:4E:9F:5F:E8:E3:91:A0:7E"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Step 4: Deploy Updated File
|
||||||
|
|
||||||
|
The file must be accessible at:
|
||||||
|
```
|
||||||
|
https://app.placebo.mk/.well-known/assetlinks.json
|
||||||
|
```
|
||||||
|
|
||||||
|
Nginx is already configured to serve this file (see `nginx.conf`).
|
||||||
|
|
||||||
|
### Step 5: Verify
|
||||||
|
|
||||||
|
Use Google's validator tool:
|
||||||
|
```bash
|
||||||
|
curl "https://digitalassetlinks.googleapis.com/v1/statements:list?source.web.site=https://app.placebo.mk&relation=delegate_permission/common.handle_all_urls"
|
||||||
|
```
|
||||||
|
|
||||||
|
Or visit:
|
||||||
|
https://digitalassetlinks.googleapis.com/v1/statements:list?source.web.site=https://app.placebo.mk
|
||||||
|
|
||||||
|
You should see your statement returned with `"debugString": "*** ERRORS parsing assetlinks.json: ..."` until you replace the placeholder.
|
||||||
|
|
||||||
|
## Troubleshooting
|
||||||
|
|
||||||
|
### File not accessible
|
||||||
|
- Check nginx configuration includes `.well-known` location
|
||||||
|
- Verify file permissions (should be readable)
|
||||||
|
- Test with: `curl https://app.placebo.mk/.well-known/assetlinks.json`
|
||||||
|
|
||||||
|
### TWA not opening properly
|
||||||
|
- Ensure SHA256 fingerprint matches your app's signing certificate
|
||||||
|
- Verify package name is exactly `mk.placebo.app`
|
||||||
|
- Check both production and debug fingerprints if testing locally
|
||||||
|
|
||||||
|
### Multiple Fingerprints
|
||||||
|
|
||||||
|
If you have both debug and release keys, add both:
|
||||||
|
```json
|
||||||
|
"sha256_cert_fingerprints": [
|
||||||
|
"14:6D:E9:... (release key)",
|
||||||
|
"AA:BB:CC:... (debug key)"
|
||||||
|
]
|
||||||
|
```
|
||||||
|
|
||||||
|
## Important Notes
|
||||||
|
|
||||||
|
- This file must be served with `Content-Type: application/json`
|
||||||
|
- The file must be accessible via HTTPS (HTTP will fail)
|
||||||
|
- Changes take effect immediately (no cache)
|
||||||
|
- Keep your signing key secure - anyone with it can create apps verified for your domain
|
||||||
|
|
||||||
|
## Resources
|
||||||
|
|
||||||
|
- [Digital Asset Links Documentation](https://developers.google.com/digital-asset-links/v1/getting-started)
|
||||||
|
- [TWA Guide](https://developers.google.com/web/android/trusted-web-activity)
|
||||||
|
- [PWABuilder Documentation](https://docs.pwabuilder.com/)
|
||||||
12
pwa/public/.well-known/assetlinks.json
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
[
|
||||||
|
{
|
||||||
|
"relation": ["delegate_permission/common.handle_all_urls"],
|
||||||
|
"target": {
|
||||||
|
"namespace": "android_app",
|
||||||
|
"package_name": "mk.placebo.app",
|
||||||
|
"sha256_cert_fingerprints": [
|
||||||
|
"PLACEHOLDER_SHA256_FINGERPRINT_FROM_PWABUILDER"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
BIN
pwa/public/assets/feature-graphic.png
Normal file
|
After Width: | Height: | Size: 15 KiB |
BIN
pwa/public/favicon.png
Normal file
|
After Width: | Height: | Size: 609 KiB |
BIN
pwa/public/icons/adaptive-background.png
Normal file
|
After Width: | Height: | Size: 338 B |
BIN
pwa/public/icons/adaptive-foreground.png
Normal file
|
After Width: | Height: | Size: 3.2 KiB |
BIN
pwa/public/icons/icon-128.png
Normal file
|
After Width: | Height: | Size: 902 B |
BIN
pwa/public/icons/icon-144.png
Normal file
|
After Width: | Height: | Size: 942 B |
BIN
pwa/public/icons/icon-152.png
Normal file
|
After Width: | Height: | Size: 987 B |
BIN
pwa/public/icons/icon-192.png
Normal file
|
After Width: | Height: | Size: 1.1 KiB |
BIN
pwa/public/icons/icon-384.png
Normal file
|
After Width: | Height: | Size: 2.3 KiB |
BIN
pwa/public/icons/icon-512-maskable.png
Normal file
|
After Width: | Height: | Size: 2.6 KiB |
BIN
pwa/public/icons/icon-512.png
Normal file
|
After Width: | Height: | Size: 2.6 KiB |
BIN
pwa/public/icons/icon-72.png
Normal file
|
After Width: | Height: | Size: 654 B |
BIN
pwa/public/icons/icon-96.png
Normal file
|
After Width: | Height: | Size: 752 B |
88
pwa/public/screenshots/README.md
Normal file
@ -0,0 +1,88 @@
|
|||||||
|
# Screenshots for Google Play Store
|
||||||
|
|
||||||
|
## Required Screenshots
|
||||||
|
|
||||||
|
You need to capture **2-8 screenshots** from the deployed PWA at https://app.placebo.mk
|
||||||
|
|
||||||
|
### How to Capture Screenshots
|
||||||
|
|
||||||
|
#### Using Chrome DevTools (Recommended)
|
||||||
|
|
||||||
|
1. Open Chrome browser
|
||||||
|
2. Navigate to https://app.placebo.mk
|
||||||
|
3. Press `F12` to open DevTools
|
||||||
|
4. Click the device toolbar icon (or press `Ctrl+Shift+M`)
|
||||||
|
5. Select device: **Pixel 5** (1080 x 2340)
|
||||||
|
6. Capture each screen:
|
||||||
|
- Click the three dots menu in device toolbar
|
||||||
|
- Select "Capture screenshot"
|
||||||
|
- Save as PNG in this directory
|
||||||
|
|
||||||
|
#### Recommended Screenshots
|
||||||
|
|
||||||
|
Capture these key screens (in order):
|
||||||
|
|
||||||
|
1. **screenshot-1-home.png** - Homepage with hero article and latest articles
|
||||||
|
2. **screenshot-2-article.png** - Article detail page showing full article
|
||||||
|
3. **screenshot-3-archive.png** - Archive page with article grid
|
||||||
|
4. **screenshot-4-live-blogs.png** - Live blogs listing page
|
||||||
|
5. **screenshot-5-live-blog-detail.png** - Live blog detail with real-time updates
|
||||||
|
6. **screenshot-6-categories.png** - Category page (Sport/Art/Science)
|
||||||
|
|
||||||
|
### Google Play Requirements
|
||||||
|
|
||||||
|
- **Format**: PNG or JPEG (PNG recommended)
|
||||||
|
- **Minimum dimensions**: 320px (shortest edge)
|
||||||
|
- **Maximum dimensions**: 3840px (longest edge)
|
||||||
|
- **Aspect ratio**: 16:9 or 9:16 recommended
|
||||||
|
- **File size**: Under 8MB per screenshot
|
||||||
|
- **Quantity**: Minimum 2, maximum 8
|
||||||
|
|
||||||
|
### Current Device Settings
|
||||||
|
|
||||||
|
Using **Pixel 5** emulation:
|
||||||
|
- Resolution: 1080 x 2340 pixels
|
||||||
|
- Pixel ratio: 2.75
|
||||||
|
- Portrait orientation
|
||||||
|
- This meets Google Play requirements perfectly
|
||||||
|
|
||||||
|
### After Capturing
|
||||||
|
|
||||||
|
Once you've captured the screenshots:
|
||||||
|
|
||||||
|
1. Name them as: `screenshot-1.png`, `screenshot-2.png`, etc.
|
||||||
|
2. Place them in this directory (`pwa/public/screenshots/`)
|
||||||
|
3. Optionally add them to the PWA manifest for better install UX
|
||||||
|
4. Upload to Google Play Console when creating the app listing
|
||||||
|
|
||||||
|
### Optional: Add to Manifest
|
||||||
|
|
||||||
|
If you want screenshots to appear in the browser install prompt, update `vite.config.ts`:
|
||||||
|
|
||||||
|
```typescript
|
||||||
|
manifest: {
|
||||||
|
// ... other config
|
||||||
|
screenshots: [
|
||||||
|
{
|
||||||
|
src: '/screenshots/screenshot-1.png',
|
||||||
|
sizes: '1080x2340',
|
||||||
|
type: 'image/png',
|
||||||
|
form_factor: 'narrow',
|
||||||
|
label: 'Homepage with latest articles',
|
||||||
|
},
|
||||||
|
// Add more screenshots here
|
||||||
|
],
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### Tips for Great Screenshots
|
||||||
|
|
||||||
|
- ✅ Use actual content (not Lorem Ipsum)
|
||||||
|
- ✅ Show the app in use with real articles
|
||||||
|
- ✅ Capture different sections to show variety
|
||||||
|
- ✅ Make sure text is readable
|
||||||
|
- ✅ Use light mode (default theme)
|
||||||
|
- ✅ Clear navigation bar and UI elements
|
||||||
|
- ❌ Don't include device frames (Google Play adds them)
|
||||||
|
- ❌ Don't add text overlays (save for marketing images)
|
||||||
|
- ❌ Don't capture error states or empty screens
|
||||||
185
pwa/src/components/routes/PrivacyPolicyComponent.tsx
Normal file
@ -0,0 +1,185 @@
|
|||||||
|
export function PrivacyPolicyComponent() {
|
||||||
|
return (
|
||||||
|
<div className="max-w-4xl mx-auto py-8">
|
||||||
|
<div className="border-brutal-lg bg-card p-8">
|
||||||
|
<h1 className="font-display text-4xl md:text-5xl mb-6">Политика за приватност</h1>
|
||||||
|
|
||||||
|
<div className="font-body space-y-6 text-muted-foreground">
|
||||||
|
<p className="text-sm text-muted-foreground/70">
|
||||||
|
Последна промена: {new Date().toLocaleDateString('mk-MK', { year: 'numeric', month: 'long', day: 'numeric' })}
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">1. Вовед</h2>
|
||||||
|
<p>
|
||||||
|
Добредојдовте на Placebo.mk ("ние", "наш", "нас"). Ја почитуваме вашата приватност и се посветени на заштитата на вашите лични податоци.
|
||||||
|
Оваа политика за приватност ви објаснува како собираме, користиме, чуваме и заштитуваме информации кога ја користите нашата апликација.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">2. Информации кои ги собираме</h2>
|
||||||
|
|
||||||
|
<h3 className="font-display text-xl text-foreground mb-2 mt-4">2.1 Автоматски собрани информации</h3>
|
||||||
|
<p>
|
||||||
|
Кога ја користите нашата апликација, автоматски собираме одредени информации за вашиот уред и користењето на апликацијата:
|
||||||
|
</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li>Тип на уред и оперативен систем</li>
|
||||||
|
<li>Верзија на прелистувач</li>
|
||||||
|
<li>IP адреса</li>
|
||||||
|
<li>Времиња на пристап и употреба</li>
|
||||||
|
<li>Страници и содржина која ја прегледувате</li>
|
||||||
|
<li>Податоци за грешки и перформанси</li>
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
<h3 className="font-display text-xl text-foreground mb-2 mt-4">2.2 Аналитика (PostHog)</h3>
|
||||||
|
<p>
|
||||||
|
Користиме PostHog за собирање анонимна аналитика за да го подобриме корисничкото искуство.
|
||||||
|
PostHog собира информации за тоа како ја користите апликацијата, вклучувајќи:
|
||||||
|
</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li>Страници што ги посетувате</li>
|
||||||
|
<li>Времетраење на посета</li>
|
||||||
|
<li>Интеракции со елементи на апликацијата</li>
|
||||||
|
<li>Технички информации за вашиот уред</li>
|
||||||
|
</ul>
|
||||||
|
<p className="mt-2">
|
||||||
|
Повеќе информации за практиките за приватност на PostHog можете да најдете на{' '}
|
||||||
|
<a
|
||||||
|
href="https://posthog.com/privacy"
|
||||||
|
target="_blank"
|
||||||
|
rel="noopener noreferrer"
|
||||||
|
className="text-accent hover:underline"
|
||||||
|
>
|
||||||
|
https://posthog.com/privacy
|
||||||
|
</a>
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<h3 className="font-display text-xl text-foreground mb-2 mt-4">2.3 Кеширани податоци</h3>
|
||||||
|
<p>
|
||||||
|
За да функционира offline, апликацијата кешира содржини (статии, слики) локално на вашиот уред користејќи Service Workers и browser cache.
|
||||||
|
</p>
|
||||||
|
|
||||||
|
<h3 className="font-display text-xl text-foreground mb-2 mt-4">2.4 Кориснички акаунти (доколку се применува)</h3>
|
||||||
|
<p>
|
||||||
|
Доколку создадете кориснички акаунт за администраторски функции, собираме:
|
||||||
|
</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li>Корисничко име</li>
|
||||||
|
<li>Email адреса</li>
|
||||||
|
<li>Хеширана лозинка</li>
|
||||||
|
<li>Улога (администратор/корисник)</li>
|
||||||
|
</ul>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">3. Како ги користиме вашите податоци</h2>
|
||||||
|
<p>Вашите податоци ги користиме за:</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li>Да ви ја обезбедиме функционалноста на апликацијата</li>
|
||||||
|
<li>Да го подобриме корисничкото искуство</li>
|
||||||
|
<li>Да анализираме како се користи апликацијата</li>
|
||||||
|
<li>Да ги идентификуваме и поправиме технички проблеми</li>
|
||||||
|
<li>Да ја заштитиме безбедноста на апликацијата</li>
|
||||||
|
<li>Да комуницираме со вас за важни промени или ажурирања</li>
|
||||||
|
</ul>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">4. Споделување на податоци</h2>
|
||||||
|
<p>
|
||||||
|
Не ги продаваме, изнајмуваме или трговаме со вашите лични податоци. Податоците може да ги споделиме само во следниве случаи:
|
||||||
|
</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li><strong>Сервиси провајдери:</strong> PostHog за аналитика (како што е опишано погоре)</li>
|
||||||
|
<li><strong>Законски барања:</strong> Кога е законски потребно или за заштита на наши права</li>
|
||||||
|
<li><strong>Деловни трансфери:</strong> Во случај на спојување, аквизиција или продажба на средства</li>
|
||||||
|
</ul>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">5. Чување на податоци</h2>
|
||||||
|
<p>
|
||||||
|
Податоците ги чуваме онолку долго колку што е потребно за целите опишани во оваа политика.
|
||||||
|
Кеширани податоци се чуваат локално на вашиот уред и може да ги избришете преку поставките на прелистувачот.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">6. Вашите права (GDPR)</h2>
|
||||||
|
<p>Според GDPR регулативата, имате право на:</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li><strong>Пристап:</strong> Да побарате копија од вашите лични податоци</li>
|
||||||
|
<li><strong>Корекција:</strong> Да побарате корекција на неточни податоци</li>
|
||||||
|
<li><strong>Бришење:</strong> Да побарате бришење на вашите податоци ("право на заборав")</li>
|
||||||
|
<li><strong>Ограничување:</strong> Да побарате ограничување на обработката</li>
|
||||||
|
<li><strong>Пренос:</strong> Да ги добиете податоците во структуриран, машински читлив формат</li>
|
||||||
|
<li><strong>Приговор:</strong> Да се спротивставите на обработката на вашите податоци</li>
|
||||||
|
</ul>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">7. Колачиња (Cookies)</h2>
|
||||||
|
<p>
|
||||||
|
Апликацијата користи технологии слични на колачиња (Service Workers, LocalStorage) за:
|
||||||
|
</p>
|
||||||
|
<ul className="list-disc list-inside ml-4 space-y-1 mt-2">
|
||||||
|
<li>Овозможување на offline функционалност</li>
|
||||||
|
<li>Зачувување на кориснички преференци</li>
|
||||||
|
<li>Аналитика (преку PostHog)</li>
|
||||||
|
</ul>
|
||||||
|
<p className="mt-2">
|
||||||
|
Можете да ги исклучите преку поставките на вашиот прелистувач, но тоа може да влијае на функционалноста.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">8. Безбедност</h2>
|
||||||
|
<p>
|
||||||
|
Превземаме соодветни технички и организациски мерки за заштита на вашите податоци од неовластен пристап,
|
||||||
|
промена, откривање или уништување. Меѓутоа, ниеден метод на пренос преку интернет или метод на електронско складирање
|
||||||
|
не е 100% безбеден.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">9. Деца</h2>
|
||||||
|
<p>
|
||||||
|
Нашата апликација не е наменета за деца под 13 години. Не собираме свесно лични информации од деца под 13 години.
|
||||||
|
Доколку сте родител или старател и знаете дека вашето дете ни дало лични информации, ве молиме контактирајте не.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">10. Промени на оваа политика</h2>
|
||||||
|
<p>
|
||||||
|
Може периодично да ја ажурираме оваа Политика за приватност. Ќе ве известиме за значајни промени со објавување
|
||||||
|
на новата политика на оваа страница и ажурирање на "Последна промена" датумот.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<h2 className="font-display text-2xl text-foreground mb-3">11. Контакт</h2>
|
||||||
|
<p>
|
||||||
|
Доколку имате прашања за оваа Политика за приватност или сакате да ги користите вашите права,
|
||||||
|
можете да не контактирате на:
|
||||||
|
</p>
|
||||||
|
<div className="mt-2 p-4 border-2 border-foreground bg-background">
|
||||||
|
<p><strong>Placebo.mk</strong></p>
|
||||||
|
<p>Email: <a href="mailto:privacy@placebo.mk" className="text-accent hover:underline">privacy@placebo.mk</a></p>
|
||||||
|
<p>Веб: <a href="https://placebo.mk" className="text-accent hover:underline">https://placebo.mk</a></p>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<section className="mt-8 pt-8 border-t-2 border-foreground/20">
|
||||||
|
<p className="text-sm text-muted-foreground/70">
|
||||||
|
Со користење на Placebo.mk апликацијата, се согласувате со оваа Политика за приватност.
|
||||||
|
Доколку не се согласувате со политиката, ве молиме не користете ја апликацијата.
|
||||||
|
</p>
|
||||||
|
</section>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
)
|
||||||
|
}
|
||||||
@ -11,6 +11,7 @@ import { AuthPage } from './components/routes/AuthPage'
|
|||||||
import { SportComponent } from './components/routes/SportComponent'
|
import { SportComponent } from './components/routes/SportComponent'
|
||||||
import { ArtComponent } from './components/routes/ArtComponent'
|
import { ArtComponent } from './components/routes/ArtComponent'
|
||||||
import { ScienceComponent } from './components/routes/ScienceComponent'
|
import { ScienceComponent } from './components/routes/ScienceComponent'
|
||||||
|
import { PrivacyPolicyComponent } from './components/routes/PrivacyPolicyComponent'
|
||||||
import { ProtectedRoute } from './components/auth/ProtectedRoute'
|
import { ProtectedRoute } from './components/auth/ProtectedRoute'
|
||||||
import { Header } from './components/layout/Header'
|
import { Header } from './components/layout/Header'
|
||||||
import { HeroArticle } from './components/home/HeroArticle'
|
import { HeroArticle } from './components/home/HeroArticle'
|
||||||
@ -57,6 +58,7 @@ const rootRoute = createRootRoute({
|
|||||||
<li><Link to="/art" className="hover:text-accent transition-colors">Уметност</Link></li>
|
<li><Link to="/art" className="hover:text-accent transition-colors">Уметност</Link></li>
|
||||||
<li><Link to="/science" className="hover:text-accent transition-colors">Наука</Link></li>
|
<li><Link to="/science" className="hover:text-accent transition-colors">Наука</Link></li>
|
||||||
<li><Link to="/archive" className="hover:text-accent transition-colors">Архива</Link></li>
|
<li><Link to="/archive" className="hover:text-accent transition-colors">Архива</Link></li>
|
||||||
|
<li><Link to="/privacy-policy" className="hover:text-accent transition-colors">Приватност</Link></li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
@ -305,6 +307,12 @@ const adminDashboardRoute = createRoute({
|
|||||||
),
|
),
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const privacyPolicyRoute = createRoute({
|
||||||
|
getParentRoute: () => rootRoute,
|
||||||
|
path: '/privacy-policy',
|
||||||
|
component: PrivacyPolicyComponent,
|
||||||
|
})
|
||||||
|
|
||||||
const routeTree = rootRoute.addChildren([
|
const routeTree = rootRoute.addChildren([
|
||||||
indexRoute,
|
indexRoute,
|
||||||
archiveRoute,
|
archiveRoute,
|
||||||
@ -318,6 +326,7 @@ const routeTree = rootRoute.addChildren([
|
|||||||
liveBlogAdminRoute,
|
liveBlogAdminRoute,
|
||||||
createLiveBlogRoute,
|
createLiveBlogRoute,
|
||||||
adminDashboardRoute,
|
adminDashboardRoute,
|
||||||
|
privacyPolicyRoute,
|
||||||
])
|
])
|
||||||
|
|
||||||
export const router = createRouter({ routeTree })
|
export const router = createRouter({ routeTree })
|
||||||
|
|||||||
@ -13,31 +13,64 @@ export default defineConfig({
|
|||||||
srcDir: 'src',
|
srcDir: 'src',
|
||||||
filename: 'sw.ts',
|
filename: 'sw.ts',
|
||||||
registerType: 'autoUpdate',
|
registerType: 'autoUpdate',
|
||||||
includeAssets: ['icons/*.svg'],
|
includeAssets: ['icons/*.png', 'icons/*.svg'],
|
||||||
manifest: {
|
manifest: {
|
||||||
name: 'Placebo.mk',
|
name: 'Placebo.mk',
|
||||||
short_name: 'Placebo',
|
short_name: 'Placebo',
|
||||||
description: 'Сатирични вести од Македонија',
|
description: 'Сатирични вести од Македонија',
|
||||||
lang: 'mk',
|
lang: 'mk',
|
||||||
start_url: '/',
|
start_url: '/',
|
||||||
|
scope: '/',
|
||||||
display: 'standalone',
|
display: 'standalone',
|
||||||
|
orientation: 'portrait-primary',
|
||||||
background_color: '#ffffff',
|
background_color: '#ffffff',
|
||||||
theme_color: '#000000',
|
theme_color: '#000000',
|
||||||
|
categories: ['news', 'entertainment'],
|
||||||
icons: [
|
icons: [
|
||||||
{
|
{
|
||||||
src: '/icons/icon-192.svg',
|
src: '/icons/icon-72.png',
|
||||||
|
sizes: '72x72',
|
||||||
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-96.png',
|
||||||
|
sizes: '96x96',
|
||||||
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-128.png',
|
||||||
|
sizes: '128x128',
|
||||||
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-144.png',
|
||||||
|
sizes: '144x144',
|
||||||
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-152.png',
|
||||||
|
sizes: '152x152',
|
||||||
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-192.png',
|
||||||
sizes: '192x192',
|
sizes: '192x192',
|
||||||
type: 'image/svg+xml',
|
type: 'image/png',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
src: '/icons/icon-512.svg',
|
src: '/icons/icon-384.png',
|
||||||
sizes: '512x512',
|
sizes: '384x384',
|
||||||
type: 'image/svg+xml',
|
type: 'image/png',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
src: '/icons/icon-512.svg',
|
src: '/icons/icon-512.png',
|
||||||
sizes: '512x512',
|
sizes: '512x512',
|
||||||
type: 'image/svg+xml',
|
type: 'image/png',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
src: '/icons/icon-512-maskable.png',
|
||||||
|
sizes: '512x512',
|
||||||
|
type: 'image/png',
|
||||||
purpose: 'maskable',
|
purpose: 'maskable',
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
|||||||