docs: sync wikis from Gitea (54 repos)
This commit is contained in:
@@ -0,0 +1,69 @@
|
||||
# ClarksvilleFurs.com
|
||||
|
||||
Managed Joomla client site for the Clarksville Furs community — a free, all-ages furry community in Clarksville, TN.
|
||||
|
||||
## Infrastructure
|
||||
|
||||
| Environment | URL | Server |
|
||||
|---|---|---|
|
||||
| **Live** | [clarksvillefurs.com](https://clarksvillefurs.com) | DreamHost (iad1-shared-b7-01) |
|
||||
| **Dev** | [clarksvillefurs.dev.mokoconsulting.tech](https://clarksvillefurs.dev.mokoconsulting.tech) | Moko Dev Server |
|
||||
| **Monitoring** | [Grafana Dashboard](https://bench.mokoconsulting.tech/d/client-d85a0ed3/) | Moko Bench |
|
||||
|
||||
Both environments share the same database. Dev is an open mirror of live (without offline mode).
|
||||
|
||||
## Quick Links
|
||||
|
||||
| Task | How |
|
||||
|---|---|
|
||||
| Deploy to dev | Push to `dev` branch → auto-deploys via workflow |
|
||||
| Deploy to live | Merge to `main` → auto-deploys dev + live |
|
||||
| Sync extensions | `deploy_sync_joomla` MCP tool or `sync-servers.yml` workflow |
|
||||
| Monitor status | [Grafana dashboard](https://bench.mokoconsulting.tech/d/client-d85a0ed3/) |
|
||||
| Run backup | Akeeba Backup in Joomla admin |
|
||||
|
||||
## Platform
|
||||
|
||||
- **CMS:** Joomla 6.1.0
|
||||
- **Template:** MokoOnyx
|
||||
- **PHP:** 8.4 (web) / 8.2 (CLI)
|
||||
- **Platform type:** `client` (MokoStandards)
|
||||
|
||||
## Documentation
|
||||
|
||||
### Site Management
|
||||
- [Deployment](deployment) — server access, deploy workflow, SFTP configs
|
||||
- [Content Authoring](content-authoring) — article and page management
|
||||
- [Brand Reference](brand-reference) — logos, colors, voice
|
||||
|
||||
### Content Guides
|
||||
- [Style Guide](authoring-style-guide) — writing standards
|
||||
- [Quick Reference](authoring-quick-reference) — common tasks
|
||||
- [Cross-Post Preview](authoring-cross-post-preview) — social media teasers
|
||||
- [Ad Schedule](authoring-ad-schedule) — promotion calendar
|
||||
|
||||
### SOPs
|
||||
- [Website Management](authoring-sop-website-management) — admin procedures
|
||||
- [Moderation](authoring-sop-moderation) — community moderation
|
||||
|
||||
### Technical
|
||||
- [Theme Architecture](theme-architecture) — MokoOnyx template structure
|
||||
- [CSS Variables](css-variables) — custom theme variables
|
||||
- [Accessibility](accessibility) — WCAG compliance
|
||||
- [Migration Plan](migration-plan-events) — events system migration
|
||||
|
||||
## MokoStandards
|
||||
|
||||
This repo follows the [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home) governance framework.
|
||||
|
||||
- [Site Monitoring](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/SITE_MONITORING) — Prometheus + Grafana monitoring
|
||||
- [Joomla Sync](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/JOOMLA_SYNC) — dev ↔ live file sync
|
||||
- [Minification](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/MINIFICATION) — CSS/JS build pipeline
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,162 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Accessibility
|
||||
|
||||
WCAG 2.1 AA is the baseline target for all text on the CF site. That means
|
||||
4.5:1 contrast for normal text and 3:1 for large text (≥18pt or ≥14pt bold) or
|
||||
UI components. This document tracks issues found during live-site audits, the
|
||||
theme-level mitigations in place, and the content-edit items that can't be
|
||||
fixed from CSS.
|
||||
|
||||
## Resolved in the theme
|
||||
|
||||
### Coral-on-sky links fail AA — fixed
|
||||
|
||||
Coral `#FF4B3E` on the sky blue backgrounds used across the site measures
|
||||
2.06:1 to 2.57:1, all below the 4.5:1 AA threshold.
|
||||
|
||||
| Fg | Bg | Ratio | Where |
|
||||
|---|---|---|---|
|
||||
| Coral | Sky Primary `#9CCEDB` | 2.33:1 | block-color-1, hero-primary |
|
||||
| Coral | Sky Secondary `#7FB7C6` | 2.06:1 | container-bottom-a, offline page bg |
|
||||
| Coral | Sky Raw `#a3cde2` | 2.57:1 | `.custom.sky` cards, container-top-b |
|
||||
|
||||
**Mitigation:** `user.css` has a scoped override that flips `--link-color` to
|
||||
ink `#1E1E1E` inside any element with a sky background (selectors cover
|
||||
`[style*="var(--color-primary)"]`, `[style*="var(--sky)"]`, `.cf-brand-callout`,
|
||||
`.container-top-b`, `.container-bottom-a`, `.hero-primary`, `.block-color-1`,
|
||||
`.custom.sky .card`, `.custom.yellow .card`, `.custom.red .card`).
|
||||
|
||||
**Hover state** uses coral, which does fail AA against sky. Hover is
|
||||
time-limited and visual affordance is already established by underline
|
||||
thickness change. Monitored but not currently a blocker.
|
||||
|
||||
### White-on-red fails AA — fixed
|
||||
|
||||
White on soft red `#ff7a73` measures 2.53:1. `.custom.red .card-body` now uses
|
||||
ink text (5.79:1, AA pass) instead of white.
|
||||
|
||||
### Muted text invisible on sky — fixed
|
||||
|
||||
Mascot Grey `#8F8F8F` on sky backgrounds drops below 2:1. Same scoped override
|
||||
bumps muted text to `#3a3a3a` inside sky surfaces.
|
||||
|
||||
### Light palette drift — fixed
|
||||
|
||||
Several Bootstrap palette variables in `light.custom.css` had accidentally held
|
||||
dark-mode values (`--light: #1B2027`, `--primary-text-emphasis: #7A1E15`,
|
||||
`--primary-bg-subtle: #3a1511`, etc.). These were silently breaking
|
||||
`.bg-primary-subtle`, `.text-primary-emphasis`, `.bg-light`, `.bg-dark` utility
|
||||
classes site-wide. All corrected to proper light-mode values in v02.02.00.
|
||||
|
||||
## Known exceptions — acceptable
|
||||
|
||||
### Coral on white, small text (3.63:1)
|
||||
|
||||
Coral on white background at body text size measures 3.63:1 — above AA-large
|
||||
(3:1) but below AA-normal (4.5:1). The `.cf-brand-accent` utility and the
|
||||
decorative `.text-danger` on headings compat rule only apply this color to
|
||||
large text (`h1`–`h6`, `.display-*`), where 3.63:1 is AA-pass. Link text with
|
||||
body font size uses a darker shade via `--link-color: #FF4B3E` + underline for
|
||||
affordance.
|
||||
|
||||
### Coral hover on dark-tint cards (1.05:1–1.39:1)
|
||||
|
||||
Hover state on `.custom.green` links is 1.39:1. Primary affordance is
|
||||
underline thickness change, which is preserved. Fix available: swap hover
|
||||
color to ink (11.4:1 AAA). Not applied by default because coral hover is the
|
||||
site-wide brand convention.
|
||||
|
||||
## Known issues — content-edit required
|
||||
|
||||
Theme CSS cannot fix these; they must be addressed in Joomla article content
|
||||
or module configuration.
|
||||
|
||||
### Placeholder URLs
|
||||
|
||||
Found in article content on about-us, faq, news:
|
||||
|
||||
```html
|
||||
<a href="/YOUR_FACEBOOK_URL">Facebook</a>
|
||||
```
|
||||
|
||||
Either replace with the real Facebook URL or remove the Facebook mention.
|
||||
|
||||
### Hardcoded brand-color CTAs
|
||||
|
||||
Home page has inline-styled Discord and Telegram CTAs:
|
||||
|
||||
```html
|
||||
```
|
||||
|
||||
Telegram's official light cyan fails AA with white text. Options:
|
||||
|
||||
1. Swap text to ink: `color: #1E1E1E` (5.09:1, AA pass)
|
||||
2. Use Telegram's darker brand variant `#0088CC` (5.09:1 with white, AA pass)
|
||||
3. Use a `.btn-primary` instead and accept that all CTAs look the same
|
||||
|
||||
All three require a content edit. Option 2 is most brand-authentic.
|
||||
|
||||
### Decorative `.text-danger` on body text
|
||||
|
||||
If an editor uses `<p class="text-danger">` to make a paragraph red (as
|
||||
decoration, not warning), the text renders as soft red `#ff7a73` — 3.14:1
|
||||
against white. Fails AA for normal text. The compat rule only applies to
|
||||
headings. For decorative red body text, use `.cf-brand-accent` (coral) instead
|
||||
— which also fails AA at body size, but is the intended brand color and is
|
||||
constrained to short spans.
|
||||
|
||||
Real semantic danger messages should stay in `.text-danger` and be kept to
|
||||
large-text usage (alerts, form validation summaries).
|
||||
|
||||
## Audit tools
|
||||
|
||||
### Style guide preview
|
||||
|
||||
Open `/style-guide.html` (at the repo root of any theme package delivery) in
|
||||
a browser. Contains:
|
||||
|
||||
- A Blue Gauntlet section exercising every common element on sky backgrounds
|
||||
- Contrast audit table computing ratios live for all common color pairs
|
||||
- Light/dark toggle
|
||||
- All tinted card variants rendered with sample content
|
||||
|
||||
### Browser DevTools
|
||||
|
||||
Chrome/Firefox DevTools Accessibility panel shows contrast ratios on hover for
|
||||
any text element. Fastest way to sanity-check a page before committing.
|
||||
|
||||
### WebAIM Contrast Checker
|
||||
|
||||
<https://webaim.org/resources/contrastchecker/> — paste in two hex values,
|
||||
confirms AA/AAA grading.
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | reference |
|
||||
| Domain | Accessibility |
|
||||
| Applies To | CF website (clarksvillefurs.com) |
|
||||
| Jurisdiction | WCAG 2.1 AA |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/accessibility.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-21 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-21 | Claude | Initial creation | Findings from live-site audit at v02.06.00 |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,89 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Authoring Documentation
|
||||
|
||||
Documentation for anyone posting Events or News articles on the
|
||||
Clarksville Furs website. Written for members of the **Event Authors**
|
||||
Joomla group and the webmaster.
|
||||
|
||||
## Who these docs are for
|
||||
|
||||
- **Event Authors** — managers and volunteers who create and publish
|
||||
event listings and news posts through the Joomla admin.
|
||||
- **Webmaster** — the person responsible for the site, user accounts,
|
||||
and cross-post integrations.
|
||||
|
||||
## Reading order
|
||||
|
||||
If you're brand new, read in this order:
|
||||
|
||||
1. **[Quick Reference](quick-reference)** — numbered steps to log
|
||||
in, create an article, attach an image, and publish. One page,
|
||||
skimmable in under a minute.
|
||||
2. **[Style Guide](style-guide)** — voice and tone rules, title
|
||||
format, body length targets, image specs, and what not to do.
|
||||
3. **[Cross-Post Preview](cross-post-preview)** — how a single
|
||||
article shows up on Discord, Telegram, and Facebook, and which
|
||||
fields control what.
|
||||
4. **[Screencast Script](screencast-script)** — the spoken script
|
||||
for the recorded walkthrough video. Read this if you want a
|
||||
scene-by-scene overview of the full workflow before you try it.
|
||||
5. **[Ad Schedule](ad-schedule)** — promotional posting schedule
|
||||
for pre-launch (4 weeks) and post-launch (6 months) to drive
|
||||
traffic to the website.
|
||||
6. **[SOP — Website Management](sop-website-management)** — user
|
||||
accounts, content management, events, media, backups, and
|
||||
emergency procedures.
|
||||
7. **[SOP — Community Moderation](sop-moderation)** — 4-tier
|
||||
moderation system, platform-specific procedures, crisis handling,
|
||||
and moderator self-care.
|
||||
|
||||
If you've posted before and just need a refresher, start and stop at
|
||||
the Quick Reference.
|
||||
|
||||
## Related documents
|
||||
|
||||
- [Migration Plan — Events](migration-plan-events) — the
|
||||
upstream plan that defines when and how Events authoring goes live.
|
||||
- [Content Authoring Guide](content-authoring) — CSS utility
|
||||
classes available inside article HTML.
|
||||
- [Brand Reference](brand-reference) — palette, typography, and
|
||||
design decisions.
|
||||
- [Deployment Guide](deployment) — how theme changes ship to
|
||||
dev and production.
|
||||
|
||||
## Questions?
|
||||
|
||||
Use the [Contact Us](https://clarksvillefurs.com/contact-us) page or ask in #server-announcements on Discord.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | index |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Event Authors group, Webmaster |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/README.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | Phase 3 authoring docs index |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,138 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Ad Schedule — Pre-Launch and Post-Launch
|
||||
|
||||
Promotional posting schedule for Discord, Telegram, and Facebook to
|
||||
build awareness of the website and drive traffic to
|
||||
clarksvillefurs.com.
|
||||
|
||||
All posts should link to the website as the primary destination — not
|
||||
to direct chat invites. The goal is to get members and newcomers
|
||||
interacting with the site, reading the FAQ, and using the events page.
|
||||
|
||||
---
|
||||
|
||||
## Pre-Launch (4 weeks before [LAUNCH DATE])
|
||||
|
||||
### Week 4 (T-28 days)
|
||||
|
||||
| Day | Platform | Post |
|
||||
|---|---|---|
|
||||
| Monday | Discord, Telegram | **Teaser**: "Something new is coming to Clarksville Furs. Stay tuned." (No link yet) |
|
||||
| Thursday | Facebook | **Teaser**: Same message, post to the Facebook group |
|
||||
|
||||
### Week 3 (T-21 days)
|
||||
|
||||
| Day | Platform | Post |
|
||||
|---|---|---|
|
||||
| Monday | Discord, Telegram | **Sneak peek**: "Our new website is almost ready. Here's a preview of what's coming — FAQ, events, and a whole new way to stay connected." Screenshot of the FAQ page. |
|
||||
| Wednesday | Facebook | **Sneak peek**: Same, with screenshot |
|
||||
| Friday | Discord | **FAQ highlight**: Share one FAQ answer as a teaser — "This and 11 more answers at clarksvillefurs.com/faq (coming soon)" |
|
||||
|
||||
### Week 2 (T-14 days)
|
||||
|
||||
| Day | Platform | Post |
|
||||
|---|---|---|
|
||||
| Monday | Discord, Telegram | **Feature spotlight — Events**: "Soon you'll be able to browse all CF events in one place — and submit your own. clarksvillefurs.com/events" |
|
||||
| Wednesday | Discord | **Feature spotlight — FAQ**: "Parents asking questions? Friends curious about the fandom? We built a FAQ page that covers it all." |
|
||||
| Friday | Facebook | **Countdown**: "One week out. The new Clarksville Furs website launches [LAUNCH DATE]." |
|
||||
|
||||
### Week 1 (T-7 days)
|
||||
|
||||
| Day | Platform | Post |
|
||||
|---|---|---|
|
||||
| Monday | All platforms | **Countdown**: "This week. clarksvillefurs.com goes live on [LAUNCH DATE]." |
|
||||
| Wednesday | Discord, Telegram | **Call to action**: "When the site launches, head to clarksvillefurs.com and explore. Read the FAQ. Check out the events page." |
|
||||
| Friday | All platforms | **Launch eve**: "Tomorrow. clarksvillefurs.com" |
|
||||
|
||||
### Launch Day
|
||||
|
||||
| Platform | Post |
|
||||
|---|---|
|
||||
| All platforms | **Launch**: "We're live! The new Clarksville Furs website is here. Explore the FAQ, browse upcoming events, and get to know the community. clarksvillefurs.com" |
|
||||
| Discord (pinned) | **Pinned**: "The Clarksville Furs website is live at clarksvillefurs.com. This is now the best place to find event details, read the FAQ, and learn about the community." |
|
||||
|
||||
---
|
||||
|
||||
## Post-Launch: Months 1–6
|
||||
|
||||
### Monthly recurring posts
|
||||
|
||||
| Frequency | Platform | Post type |
|
||||
|---|---|---|
|
||||
| 1st of month | All platforms | **Monthly reminder**: "All upcoming events are on clarksvillefurs.com/events. Browse what's coming up and RSVP." |
|
||||
| 15th of month | Discord, Telegram | **Submit your own event**: "Did you know members can create their own events? Visit clarksvillefurs.com/events and click Submit Event." |
|
||||
| Weekly (Mon) | Discord | **FAQ of the week**: Pick one FAQ article and share the intro text with a link. Rotate through all 12 over 3 months. |
|
||||
|
||||
### Month 1 — Establish habits
|
||||
|
||||
| Week | Platform | Post |
|
||||
|---|---|---|
|
||||
| 1 | All platforms | **Welcome post**: "New here? Start at clarksvillefurs.com — our FAQ answers the most common questions, and the events page shows you what's coming up." |
|
||||
| 2 | Discord, Telegram | **For parents**: "Got a kid who's into furries? Our FAQ has a page just for you: clarksvillefurs.com/faq" |
|
||||
| 3 | Facebook | **Share prompt**: "Know someone curious about the fandom? Share our FAQ with them: clarksvillefurs.com/faq" |
|
||||
| 4 | Discord | **Event submission reminder**: "Want to organize a game night, movie night, or meetup? Submit it at clarksvillefurs.com/events" |
|
||||
|
||||
### Month 2 — Deepen engagement
|
||||
|
||||
| Week | Platform | Post |
|
||||
|---|---|---|
|
||||
| 1 | Discord, Telegram | **Highlight a specific FAQ**: "What is a Therian?" intro text + link |
|
||||
| 2 | Facebook | **Convention planning**: "Thinking about a con trip? Check our events page for group plans: clarksvillefurs.com/events" |
|
||||
| 3 | Discord | **Feedback ask**: "Been using the website? Tell us what you think — use the Contact Us page: clarksvillefurs.com/contact-us" |
|
||||
| 4 | All platforms | **Community stat**: "X members and counting. If you haven't visited the site yet, now's a great time: clarksvillefurs.com" |
|
||||
|
||||
### Months 3–6 — Maintain cadence
|
||||
|
||||
By month 3, reduce to the monthly recurring schedule (1st and 15th)
|
||||
plus the weekly FAQ rotation on Discord. Add one-off posts only when:
|
||||
|
||||
- A new FAQ article is added
|
||||
- A major event is coming up
|
||||
- The website gets a significant update
|
||||
- A milestone is reached (member count, event count)
|
||||
|
||||
---
|
||||
|
||||
## Post guidelines
|
||||
|
||||
- **Always link to clarksvillefurs.com** — never give out direct
|
||||
Discord or Telegram invite links as the primary entry point
|
||||
- **Teasers, not full details** — drive traffic to the website for
|
||||
complete information
|
||||
- **Contact goes through the ticket system** — point people to
|
||||
clarksvillefurs.com/contact-us, not a direct email address
|
||||
- **Keep it casual** — match the CF voice (warm, direct, inclusive)
|
||||
- **One exclamation mark max** per post
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | schedule |
|
||||
| Domain | Content Marketing |
|
||||
| Applies To | Webmaster, Event Authors, Social media managers |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/ad-schedule.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Draft |
|
||||
| Last Reviewed | 2026-04-27 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-27 | Claude | Initial creation | Pre-launch (4 weeks) and post-launch (6 months) promotional schedule |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,238 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Cross-Post Preview
|
||||
|
||||
When you publish an article in the **Events** or **News** category, it
|
||||
automatically cross-posts to three platforms. Each platform pulls
|
||||
different fields from the article. This page shows you exactly what
|
||||
goes where so you can tune your intro text and image before hitting
|
||||
Publish.
|
||||
|
||||
## How cross-posting works
|
||||
|
||||
Two integrations handle the cross-posts:
|
||||
|
||||
| Integration | Destination | Trigger |
|
||||
|---|---|---|
|
||||
| **MokoDiscordHook** | Discord — #server-announcements | `onContentAfterSave` fires when an article is saved in a configured category |
|
||||
| **Perfect Publisher** | Facebook Page + Telegram channel | Rule Engine matches the article category and posts via the FB and Telegram APIs |
|
||||
|
||||
You don't need to do anything extra. Save a published article in the
|
||||
right category and the cross-posts fire automatically.
|
||||
|
||||
**Important — teasers, not full details.** Cross-posts should hook the
|
||||
reader and drive them to the website. Write the intro as a short teaser
|
||||
that makes people want to click through to clarksvillefurs.com/events
|
||||
for the full info. Don't put the complete date, time, and location in
|
||||
the intro — save those for the article body.
|
||||
|
||||
## Worked example
|
||||
|
||||
Suppose you create this article:
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **Title** | Monthly Meetup — Downtown Clarksville |
|
||||
| **Alias** | monthly-meetup-downtown-clarksville |
|
||||
| **Category** | Events |
|
||||
| **Intro text** | Our monthly meetup is back! Grab a lawn chair and come hang — full details on the website. |
|
||||
| **Intro Image** | `images/events/meetup-heritage-park.jpg` (1200x630, pavilion with picnic tables) |
|
||||
| **Intro Image Alt** | Pavilion at Heritage Park with picnic tables and string lights |
|
||||
| **Full article body** | (additional details: directions, parking, what to bring, RSVP link) |
|
||||
|
||||
Here's how that article renders on each surface:
|
||||
|
||||
---
|
||||
|
||||
### Discord — MokoDiscordHook embed
|
||||
|
||||
MokoDiscordHook sends a rich embed to #server-announcements. The
|
||||
embed uses these article fields:
|
||||
|
||||
| Embed element | Sourced from |
|
||||
|---|---|
|
||||
| **Embed title** | Article title |
|
||||
| **Embed description** | Intro text (first 1–2 sentences of the article body, before the "Read more" break) |
|
||||
| **Embed image** | Intro Image |
|
||||
| **Embed link** | Full article URL on clarksvillefurs.com |
|
||||
|
||||
**What it looks like in Discord:**
|
||||
|
||||
```
|
||||
┌──────────────────────────────────────────┐
|
||||
│ Monthly Meetup — Downtown Clarksville │
|
||||
│ │
|
||||
│ Our monthly meetup is back! Grab a │
|
||||
│ lawn chair and come hang — full │
|
||||
│ details on the website. │
|
||||
│ │
|
||||
│ │
|
||||
│ ┌────────────────────────────────────┐ │
|
||||
│ │ │ │
|
||||
│ │ [ intro image: pavilion with │ │
|
||||
│ │ picnic tables and string │ │
|
||||
│ │ lights ] │ │
|
||||
│ │ │ │
|
||||
│ └────────────────────────────────────┘ │
|
||||
│ │
|
||||
│ clarksvillefurs.com │
|
||||
└──────────────────────────────────────────┘
|
||||
```
|
||||
|
||||
**Tips for Discord:**
|
||||
|
||||
- Keep the intro under 200 characters for clean embed layout.
|
||||
- Title truncates around 70 characters — stay under.
|
||||
- The image renders full-width in the embed. Landscape (1200x630) is
|
||||
ideal.
|
||||
- Discord caches embeds aggressively. If you edit the article after
|
||||
posting, the Discord embed will **not** update.
|
||||
|
||||
---
|
||||
|
||||
### Telegram — Perfect Publisher message
|
||||
|
||||
Perfect Publisher posts to @ClarksvilleFurs as a text message
|
||||
with a link preview.
|
||||
|
||||
| Message element | Sourced from |
|
||||
|---|---|
|
||||
| **Message text** | Intro text + article URL |
|
||||
| **Link preview title** | Article title (from the page's `<meta og:title>`) |
|
||||
| **Link preview image** | Intro Image (from `<meta og:image>`) |
|
||||
| **Link preview description** | Meta description, or intro text if meta description is empty |
|
||||
|
||||
**What it looks like in Telegram:**
|
||||
|
||||
```
|
||||
Our monthly meetup is back! Grab a lawn
|
||||
chair and come hang — full details on
|
||||
the website.
|
||||
|
||||
clarksvillefurs.com/events/monthly-meetup-
|
||||
downtown-clarksville
|
||||
|
||||
┌────────────────────────────────┐
|
||||
│ [ link preview card ] │
|
||||
│ │
|
||||
│ Monthly Meetup — Downtown │
|
||||
│ Clarksville │
|
||||
│ │
|
||||
│ [ intro image thumbnail ] │
|
||||
│ │
|
||||
│ clarksvillefurs.com │
|
||||
└────────────────────────────────┘
|
||||
```
|
||||
|
||||
**Tips for Telegram:**
|
||||
|
||||
- The intro text becomes the message body — write it as a teaser that
|
||||
hooks the reader and drives them to the website for full details.
|
||||
- Telegram generates the link preview from Open Graph meta tags. If the
|
||||
intro image is missing, Telegram may show no preview or a generic
|
||||
favicon.
|
||||
- The link preview caches. If you need to refresh it after editing,
|
||||
use Telegram's [@webpagebot](https://t.me/webpagebot) to clear the
|
||||
cache for the URL.
|
||||
|
||||
---
|
||||
|
||||
### Facebook — Perfect Publisher post
|
||||
|
||||
Perfect Publisher creates a post on the linked Facebook Page
|
||||
(clarksvillefurs) with a link card.
|
||||
|
||||
| Post element | Sourced from |
|
||||
|---|---|
|
||||
| **Post text** | Intro text (prepended to the link) |
|
||||
| **Link card title** | Article title (from `<meta og:title>`) |
|
||||
| **Link card image** | Intro Image (from `<meta og:image>`) |
|
||||
| **Link card description** | Meta description, or intro text if empty |
|
||||
| **Link card domain** | clarksvillefurs.com |
|
||||
|
||||
**What it looks like on Facebook:**
|
||||
|
||||
```
|
||||
Clarksville Furs
|
||||
Just now · 🌐
|
||||
|
||||
Our monthly meetup is back! Grab a lawn
|
||||
chair and come hang — full details on
|
||||
the website.
|
||||
|
||||
┌────────────────────────────────────┐
|
||||
│ │
|
||||
│ [ large link card image: │
|
||||
│ pavilion with picnic tables │
|
||||
│ and string lights ] │
|
||||
│ │
|
||||
├────────────────────────────────────┤
|
||||
│ CLARKSVILLEFURS.COM │
|
||||
│ Monthly Meetup — Downtown │
|
||||
│ Clarksville │
|
||||
│ Our monthly meetup is back! │
|
||||
│ Grab a lawn chair and come... │
|
||||
└────────────────────────────────────┘
|
||||
|
||||
👍 Like 💬 Comment ↗ Share
|
||||
```
|
||||
|
||||
**Tips for Facebook:**
|
||||
|
||||
- The link card image must be at least 600x315 px. The recommended
|
||||
1200x630 works perfectly.
|
||||
- Facebook caches link previews aggressively. If you update the image
|
||||
or title after the first post, use the Facebook Sharing Debugger to
|
||||
force a re-scrape of the URL.
|
||||
- The intro text appears *above* the link card. Keep it short and
|
||||
punchy — two sentences max.
|
||||
|
||||
---
|
||||
|
||||
## Field-to-surface cheat sheet
|
||||
|
||||
| Article field | Website | Discord | Telegram | Facebook |
|
||||
|---|---|---|---|---|
|
||||
| Title | Page heading | Embed title | Link preview title | Link card title |
|
||||
| Intro text | Category listing excerpt | Embed description | Message body | Post text |
|
||||
| Intro Image | Category listing thumbnail | Embed image | Link preview image | Link card image |
|
||||
| Intro Image Alt | `alt` attribute on `<img>` | Not displayed | Not displayed | Not displayed (but good practice) |
|
||||
| Full article body | Full article page | Not included | Not included | Not included |
|
||||
| Article URL | Canonical link | Embed link | Message link | Link card URL |
|
||||
| Meta description | `<meta name="description">` | Not used | Link preview fallback | Link card fallback |
|
||||
|
||||
**Key takeaway:** The **intro text** and **intro image** are the two
|
||||
fields that matter most for cross-posts. Get those right and every
|
||||
platform looks good.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | guide |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Event Authors group, Webmaster |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/cross-post-preview.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | Phase 3 cross-post field mapping with worked example |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,100 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Quick Reference — Events and News
|
||||
|
||||
One-page cheat sheet. If you've posted before and just forgot the
|
||||
steps, this should get you unblocked in under a minute.
|
||||
|
||||
## Log in
|
||||
|
||||
1. Go to `clarksvillefurs.com/administrator`
|
||||
2. Enter your username and password.
|
||||
3. Complete the 2FA prompt (authenticator app code).
|
||||
4. You land on the Home Dashboard.
|
||||
|
||||
## Create a new article
|
||||
|
||||
5. From the Home Dashboard, click **Content > Articles > + New**.
|
||||
6. Enter the **Title** — use the format described in the
|
||||
[Style Guide](./style-guide.md#title-format).
|
||||
7. Set the **Alias** — Joomla auto-generates one from the title. Leave
|
||||
it unless you need a shorter URL slug.
|
||||
8. Set the **Category**:
|
||||
- **Events** for event listings.
|
||||
- **News** for announcements and updates.
|
||||
|
||||
## Write the body
|
||||
|
||||
9. Write a 1–2 sentence intro paragraph. This is the text that
|
||||
appears in cross-posts to Discord, Telegram, and Facebook — make
|
||||
it count.
|
||||
10. Add the rest of the article body. See the
|
||||
[Style Guide](./style-guide.md#body-length-targets) for length
|
||||
guidance.
|
||||
|
||||
## Attach an image
|
||||
|
||||
11. In the **Images** tab (below the editor):
|
||||
- **Intro Image** — shown in category list views and cross-posts.
|
||||
- **Full Article Image** — shown at the top of the full article.
|
||||
12. Click **Select** and upload or pick from the Media Manager.
|
||||
13. Fill in the **Alt Text** field — describe what's in the image.
|
||||
See [Style Guide — Image specs](./style-guide.md#image-specs).
|
||||
|
||||
## Set the publish date
|
||||
|
||||
14. In the **Publishing** tab:
|
||||
- **Start Publishing** — set the date and time the article should
|
||||
go live. Use this for scheduling future events.
|
||||
- Leave **Finish Publishing** blank unless the article should
|
||||
auto-expire.
|
||||
|
||||
## Publish
|
||||
|
||||
15. Set **Status** to **Published** (green toggle at the top).
|
||||
16. Click **Save & Close**.
|
||||
|
||||
## Verify
|
||||
|
||||
17. Open the site in a new tab and confirm the article appears in the
|
||||
correct category listing.
|
||||
18. Check that the intro image renders and the title is correct.
|
||||
19. Wait 1–2 minutes, then verify the cross-posts arrived:
|
||||
- Discord — #server-announcements
|
||||
- Telegram — @ClarksvilleFurs
|
||||
- Facebook — linked Facebook Page
|
||||
|
||||
If a cross-post didn't arrive, check the article category. Cross-posts
|
||||
only fire for articles saved in the **Events** or **News** categories.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | guide |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Event Authors group, Webmaster |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/quick-reference.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | Phase 3 quick-reference cheat sheet |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,245 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Screencast Script — Events and News Walkthrough
|
||||
|
||||
**Runtime target:** 5–8 minutes
|
||||
**Presenter:** Moko Consulting (to be assigned)
|
||||
**Format:** Screen recording with voiceover
|
||||
|
||||
This is the read-from script for the recorded walkthrough. Screen
|
||||
directions are in `[BRACKETS]`. Spoken voiceover is the plain text
|
||||
beneath each direction.
|
||||
|
||||
---
|
||||
|
||||
## Scene 1 — Intro (0:00–0:30)
|
||||
|
||||
`[SCREEN: CF website homepage, scrolled to show the Events section]`
|
||||
|
||||
Hey everyone! This is a quick walkthrough of how to post events and
|
||||
news on the Clarksville Furs website. By the end of this video you'll
|
||||
know how to log in, create an article, attach an image, and publish —
|
||||
plus you'll see how your post automatically shows up on Discord,
|
||||
Telegram, and Facebook.
|
||||
|
||||
Let's jump in.
|
||||
|
||||
---
|
||||
|
||||
## Scene 2 — Logging in (0:30–1:15)
|
||||
|
||||
`[SCREEN: Browser navigating to clarksvillefurs.com/administrator]`
|
||||
|
||||
First, head to clarksvillefurs.com/administrator. This is the Joomla
|
||||
admin panel — it's where all content management happens.
|
||||
|
||||
`[SCREEN: Joomla login form — type username and password]`
|
||||
|
||||
Enter your username and password. These were set up for you when your
|
||||
account was created. If you don't have credentials yet, reach out to
|
||||
the [Contact Us](https://clarksvillefurs.com/contact-us) page.
|
||||
|
||||
`[SCREEN: 2FA prompt — enter authenticator code]`
|
||||
|
||||
You'll also need to enter a code from your authenticator app. This
|
||||
is two-factor authentication — it keeps the site secure even if your
|
||||
password gets compromised.
|
||||
|
||||
`[SCREEN: Home Dashboard loads]`
|
||||
|
||||
And we're in. This is the Home Dashboard. You can see quick links to
|
||||
articles, media, and users. We're going to create a new article.
|
||||
|
||||
---
|
||||
|
||||
## Scene 3 — Creating the article (1:15–2:45)
|
||||
|
||||
`[SCREEN: Click Content > Articles > + New in the top menu]`
|
||||
|
||||
Click **Content**, then **Articles**, then the **New** button. This
|
||||
opens a blank article editor.
|
||||
|
||||
`[SCREEN: Article editor — cursor in Title field]`
|
||||
|
||||
Start with the title. For events, we use the format "Event Name — em
|
||||
dash — Location." So for our monthly meetup, that's "Monthly Meetup —
|
||||
Downtown Clarksville."
|
||||
|
||||
`[SCREEN: Type the title "Monthly Meetup — Downtown Clarksville"]`
|
||||
|
||||
Keep it under 70 characters so it doesn't get cut off in Discord
|
||||
embeds.
|
||||
|
||||
`[SCREEN: Click the Category dropdown, select "Events"]`
|
||||
|
||||
Next, set the category. Pick **Events** for event listings or **News**
|
||||
for announcements. This is important — the category controls which
|
||||
cross-post integrations fire. If you pick the wrong category, your
|
||||
post won't show up on Discord or Telegram.
|
||||
|
||||
`[SCREEN: Click into the editor body area]`
|
||||
|
||||
Now write the body. Start with one or two sentences that summarize the
|
||||
event — the what, when, and where. This intro text is what people see
|
||||
on Discord, Telegram, and Facebook before they click through, so make
|
||||
it count.
|
||||
|
||||
`[SCREEN: Type intro text: "Come hang out with us this Saturday! We're meeting at the pavilion in Heritage Park, 12–3 PM. Bring a lawn chair and a good attitude."]`
|
||||
|
||||
After the intro, add whatever details people need: directions, parking,
|
||||
what to bring, an RSVP link. But keep it concise — 50 to 150 words is
|
||||
plenty for an event listing.
|
||||
|
||||
---
|
||||
|
||||
## Scene 4 — Adding an image (2:45–4:00)
|
||||
|
||||
`[SCREEN: Click the "Images" tab below the editor]`
|
||||
|
||||
Scroll down and click the **Images** tab. You'll see two image slots:
|
||||
Intro Image and Full Article Image.
|
||||
|
||||
`[SCREEN: Click "Select" next to Intro Image]`
|
||||
|
||||
The **Intro Image** is the one that matters most. It shows up in the
|
||||
category listing on the website and in every cross-post. Click
|
||||
**Select** to open the Media Manager.
|
||||
|
||||
`[SCREEN: Media Manager — upload a new image or select an existing one]`
|
||||
|
||||
You can upload a new image or pick one that's already in the library.
|
||||
For best results, use a landscape photo — 1200 by 630 pixels. Keep the
|
||||
file size under 500 KB. JPG works great for photos.
|
||||
|
||||
`[SCREEN: Select the image, return to the Images tab]`
|
||||
|
||||
Once you've picked the image, fill in the **Alt Text** field. This is
|
||||
a short description of what's *in* the image — not the event title.
|
||||
Something like "Pavilion at Heritage Park with picnic tables and string
|
||||
lights." Screen readers use this, and it's good practice for
|
||||
accessibility.
|
||||
|
||||
`[SCREEN: Type alt text into the Alt Text field]`
|
||||
|
||||
Don't skip the alt text. It takes five seconds and makes the site
|
||||
better for everyone.
|
||||
|
||||
---
|
||||
|
||||
## Scene 5 — Publishing options (4:00–5:00)
|
||||
|
||||
`[SCREEN: Click the "Publishing" tab]`
|
||||
|
||||
Click the **Publishing** tab. The main field here is **Start
|
||||
Publishing** — this is when the article goes live on the site.
|
||||
|
||||
`[SCREEN: Set Start Publishing to a date a few days from now]`
|
||||
|
||||
For events, I like to set this a few days before the event so people
|
||||
have time to see it and plan. You can also set **Finish Publishing** if
|
||||
you want the article to automatically disappear after the event date,
|
||||
but that's optional.
|
||||
|
||||
`[SCREEN: Scroll up to the Status toggle at the top]`
|
||||
|
||||
Last thing before we save — make sure the **Status** is set to
|
||||
**Published**. It's the green toggle at the top of the editor. If this
|
||||
is set to Unpublished, the article exists but nobody can see it.
|
||||
|
||||
---
|
||||
|
||||
## Scene 6 — Save and verify (5:00–6:00)
|
||||
|
||||
`[SCREEN: Click "Save & Close" in the toolbar]`
|
||||
|
||||
Click **Save & Close**. Joomla saves the article and drops you back to
|
||||
the article list.
|
||||
|
||||
`[SCREEN: Open the site frontend in a new tab, navigate to the Events category]`
|
||||
|
||||
Let's verify. Open the site in a new tab and navigate to the Events
|
||||
page. There's our article — title, intro text, and the image we just
|
||||
uploaded.
|
||||
|
||||
`[SCREEN: Click into the full article to show the complete content]`
|
||||
|
||||
Click into it to see the full article. Everything looks good.
|
||||
|
||||
---
|
||||
|
||||
## Scene 7 — Cross-post verification (6:00–7:00)
|
||||
|
||||
`[SCREEN: Switch to Discord — show the channel with the new embed]`
|
||||
|
||||
Now let's check the cross-posts. Over in Discord, in the
|
||||
#server-announcements channel, you can see the embed that fired
|
||||
automatically when we saved the article. It pulled in the title, the
|
||||
intro text, the image, and a link back to the full article on the
|
||||
website.
|
||||
|
||||
`[SCREEN: Switch to Telegram — show the channel message]`
|
||||
|
||||
Same thing on Telegram. The intro text is the message body, and
|
||||
there's a link preview card with the title and image.
|
||||
|
||||
`[SCREEN: Switch to Facebook — show the page post]`
|
||||
|
||||
And on Facebook — the page post has the intro text above a link card
|
||||
with the image and title.
|
||||
|
||||
All three platforms pulled from the same two fields: the **intro text**
|
||||
and the **intro image**. That's why those two fields matter the most.
|
||||
|
||||
---
|
||||
|
||||
## Scene 8 — Wrap-up (7:00–7:30)
|
||||
|
||||
`[SCREEN: Back on the CF website Events page]`
|
||||
|
||||
That's the whole workflow. To recap:
|
||||
|
||||
1. Log in with your credentials and 2FA code.
|
||||
2. Create a new article — set the title, category, and body.
|
||||
3. Attach an intro image with alt text.
|
||||
4. Set the publish date and status.
|
||||
5. Save, verify on the website, and confirm the cross-posts arrived.
|
||||
|
||||
If you get stuck, check the Quick Reference doc — it's a one-page
|
||||
cheat sheet with all the steps. And if something's not working, reach
|
||||
out to the [Contact Us](https://clarksvillefurs.com/contact-us) page.
|
||||
|
||||
Thanks for watching, and happy posting!
|
||||
|
||||
`[SCREEN: Fade to CF logo / end card]`
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | script |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Screencast recording — Moko Consulting presenter |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/screencast-script.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Draft |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | Phase 3 walkthrough script, 8 scenes, ~7 min target |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,488 @@
|
||||
← [Home](Home)
|
||||
|
||||
# SOP — Community Moderation
|
||||
|
||||
Standard operating procedures for moderating the Clarksville Furs
|
||||
community across all platforms: the website, Discord, Telegram, and
|
||||
Facebook.
|
||||
|
||||
Clarksville Furs is an all-ages, family-friendly community. These
|
||||
procedures exist to keep it that way.
|
||||
|
||||
---
|
||||
|
||||
## 1. Guiding Principles
|
||||
|
||||
- **Safety first** — protect minors, protect vulnerable members,
|
||||
protect the community's reputation.
|
||||
- **Assume good intent** — most issues are misunderstandings, not
|
||||
malice. Educate before you escalate.
|
||||
- **Consistency** — enforce the same standards everywhere. What's not
|
||||
okay on Discord is not okay on Telegram, Facebook, or the website.
|
||||
- **Transparency** — when you take moderation action, explain why.
|
||||
Members deserve to know what rule was broken.
|
||||
- **Documentation** — log every moderation action. Patterns matter
|
||||
more than individual incidents.
|
||||
|
||||
---
|
||||
|
||||
## 2. Community Guidelines Summary
|
||||
|
||||
The full Community Guidelines are published at
|
||||
`clarksvillefurs.com/community-guidelines`. Key rules for moderators:
|
||||
|
||||
1. **All-ages content only** in all public spaces
|
||||
2. **No harassment, bullying, or targeted behavior**
|
||||
3. **No hate speech** — racism, homophobia, transphobia, or any
|
||||
identity-based attacks
|
||||
4. **No unsolicited sexual content** in any public space
|
||||
5. **No doxxing** — sharing someone's real name, address, workplace,
|
||||
or photo without consent
|
||||
6. **No spam or self-promotion** without moderator approval
|
||||
7. **Respect pronouns and chosen names**
|
||||
8. **No drama-baiting** — deliberately provocative posts designed to
|
||||
start arguments
|
||||
|
||||
---
|
||||
|
||||
## 3. Moderation Tiers
|
||||
|
||||
Not every issue requires the same response. Use the tier system to
|
||||
match the response to the severity.
|
||||
|
||||
### Tier 1 — Gentle reminder (most common)
|
||||
|
||||
**When to use:** First-time minor infractions. Off-topic posting,
|
||||
mild language in a family-friendly channel, accidental oversharing.
|
||||
|
||||
**Action:**
|
||||
1. Send a friendly DM (not a public callout).
|
||||
2. Explain which guideline was relevant.
|
||||
3. Ask them to edit or delete the message.
|
||||
4. No formal record unless it recurs.
|
||||
|
||||
**Example script:**
|
||||
> Hey! Just a heads-up — we keep things family-friendly in the public
|
||||
> channels. Would you mind editing/removing that message? Thanks!
|
||||
|
||||
### Tier 2 — Formal warning
|
||||
|
||||
**When to use:** Repeat minor infractions after a Tier 1 reminder, or
|
||||
a single moderate infraction (heated argument, inappropriate content
|
||||
that's not extreme, disrespectful behavior).
|
||||
|
||||
**Action:**
|
||||
1. DM the member with a clear statement of what happened and which
|
||||
rule was broken.
|
||||
2. Delete or hide the offending content.
|
||||
3. Log the warning in the moderation log (see Section 7).
|
||||
4. Inform other moderators so they're aware.
|
||||
|
||||
**Example script:**
|
||||
> Hi — this is a formal warning about [specific behavior] in
|
||||
> [channel/platform]. This violates our Community Guidelines,
|
||||
> specifically [rule number/name]. Please review the guidelines at
|
||||
> clarksvillefurs.com/community-guidelines. Further violations may
|
||||
> result in a temporary or permanent ban.
|
||||
|
||||
### Tier 3 — Temporary ban (24 hours to 30 days)
|
||||
|
||||
**When to use:** Serious single infractions or pattern of Tier 2
|
||||
warnings (3+ warnings in 90 days). Examples: explicit content in a
|
||||
public channel, targeted harassment, sustained disruptive behavior.
|
||||
|
||||
**Action:**
|
||||
1. Mute or ban the member on the affected platform.
|
||||
2. DM them with the reason and duration.
|
||||
3. Log in the moderation log with full context.
|
||||
4. Notify the moderation team.
|
||||
5. After the ban expires, send a welcome-back message reminding them
|
||||
of the guidelines.
|
||||
|
||||
**Duration guidelines:**
|
||||
- First temp ban: 24–72 hours
|
||||
- Second temp ban: 7–14 days
|
||||
- Third temp ban: 30 days, with a note that the next step is permanent
|
||||
|
||||
### Tier 4 — Permanent ban
|
||||
|
||||
**When to use:** Extreme violations (threats, doxxing, CSAM, predatory
|
||||
behavior toward minors) or failure to reform after multiple Tier 3
|
||||
bans.
|
||||
|
||||
**Action:**
|
||||
1. Immediately ban on all platforms (Discord, Telegram, Facebook,
|
||||
website).
|
||||
2. Do not engage in debate — the decision is final.
|
||||
3. Log the full incident with screenshots and timestamps.
|
||||
4. Notify the webmaster and Moko Consulting.
|
||||
5. If the violation involves a minor or is potentially criminal,
|
||||
see Section 6.
|
||||
|
||||
---
|
||||
|
||||
## 4. Platform-Specific Procedures
|
||||
|
||||
### 4.1 Discord
|
||||
|
||||
- **Roles**: Moderators have the `Content Moderators` role with
|
||||
permissions to delete messages, mute members, and manage channels.
|
||||
- **Slow mode**: Enable slow mode (30–60 seconds) during heated
|
||||
conversations instead of immediately banning.
|
||||
- **Channel locks**: Lock a channel temporarily if a situation is
|
||||
escalating. Announce: "Channel is paused while mods review. Be
|
||||
back shortly."
|
||||
- **DM policy**: Always DM the member before or after taking public
|
||||
action. Never moderate silently — it breeds distrust.
|
||||
- **Bot logs**: Check the audit log and bot logs for context before
|
||||
acting.
|
||||
|
||||
### 4.2 Telegram
|
||||
|
||||
- **Admin rights**: Moderators have admin rights in the main chat
|
||||
group.
|
||||
- **Announcement channel** (@ClarksvilleFurs): Only admins can post.
|
||||
No moderation needed — it's outbound only.
|
||||
- **Main chat group**: Apply the same tier system as Discord.
|
||||
- **Spam bots**: Telegram is prone to join-spam. Use the group's
|
||||
anti-spam bot and manually remove/ban spam accounts immediately.
|
||||
|
||||
### 4.3 Facebook group
|
||||
|
||||
- **Admin/Moderator roles**: Moderators have the Moderator role on the
|
||||
Facebook group.
|
||||
- **Post approval**: Consider enabling post approval for new members
|
||||
(first 30 days) to catch spam and inappropriate content before it's
|
||||
visible.
|
||||
- **Reporting**: Facebook has its own reporting system. If someone
|
||||
reports a post, review it promptly — Facebook may act independently
|
||||
if reports pile up.
|
||||
- **Non-members**: The group is public, so non-members can see content.
|
||||
Moderate accordingly — assume parents and employers are reading.
|
||||
|
||||
### 4.4 Website (Joomla)
|
||||
|
||||
Content Moderators have Joomla admin panel access and can manage
|
||||
content directly.
|
||||
|
||||
- **Admin access**: Content Moderators can log in at
|
||||
`clarksvillefurs.com/administrator` to manage articles and events.
|
||||
- **User blocking**: Go to **Users > Manage**, find the user, set
|
||||
**Block User** to Yes.
|
||||
- **Content removal**: Unpublish the article or event immediately.
|
||||
Investigate before permanently deleting — you may need the content
|
||||
as evidence.
|
||||
- **Event review**: Event Authors can auto-publish DPCalendar events.
|
||||
Review recently published events periodically and unpublish anything
|
||||
that violates Community Guidelines.
|
||||
- **Protected categories**: Content Moderators cannot edit FAQ, About
|
||||
Us, Legal, SOP, or News articles. Escalate to a Manager if changes
|
||||
are needed in those categories.
|
||||
- **Registration spam**: Check the Community Builder approval queue
|
||||
regularly. Reject accounts with obviously fake names, disposable
|
||||
emails, or no profile information.
|
||||
|
||||
---
|
||||
|
||||
## 5. In-Person Event Moderation
|
||||
|
||||
### 5.1 Meetup ground rules
|
||||
|
||||
All Clarksville Furs meetups follow the same Community Guidelines as
|
||||
online spaces. Additionally:
|
||||
|
||||
- **All-ages environment** — no alcohol at CF-organized events unless
|
||||
the venue is 21+ only and the event is explicitly labeled as such.
|
||||
- **Photography consent** — ask before photographing or filming anyone.
|
||||
Never photograph minors without explicit parental consent. Fursuiters
|
||||
may be photographed in public spaces unless they ask not to be.
|
||||
- **Personal space** — not everyone wants hugs. Ask first. "Can I hug
|
||||
you?" is always the right question.
|
||||
- **No weapons** — real or prop. Even if it's part of a costume.
|
||||
|
||||
### 5.2 Handling issues at a meetup
|
||||
|
||||
If someone is making others uncomfortable or violating guidelines:
|
||||
|
||||
1. Pull them aside privately — do not make a scene.
|
||||
2. Explain the issue calmly and specifically.
|
||||
3. If they cooperate, move on. No need to escalate.
|
||||
4. If they refuse or the behavior is serious, ask them to leave.
|
||||
Be firm but not aggressive: "I need you to head out for today.
|
||||
We can talk about this later."
|
||||
5. If they refuse to leave or become threatening, call 911. Do not
|
||||
physically confront anyone.
|
||||
6. Log the incident after the event. Follow the tier system for any
|
||||
online follow-up.
|
||||
|
||||
### 5.3 Photography and social media at events
|
||||
|
||||
- **Before the event**: Announce in Discord/Telegram that photos will
|
||||
be taken and may be shared on CF social media.
|
||||
- **At the event**: Designate a photographer if possible. Ask for
|
||||
verbal consent before posting photos of identifiable people.
|
||||
- **Minors**: Never post photos of minors on CF social media without
|
||||
written parental consent. When in doubt, don't post it.
|
||||
- **Fursuiters**: Fursuiters in public spaces generally expect to be
|
||||
photographed, but always respect a "no photos" request.
|
||||
|
||||
### 5.4 Venue-specific rules
|
||||
|
||||
Some venues have their own rules (no outside food, specific parking,
|
||||
noise limits). The event organizer should:
|
||||
|
||||
1. Visit the venue beforehand or call to confirm rules.
|
||||
2. Post venue rules in the event description.
|
||||
3. Remind attendees at the start of the meetup.
|
||||
4. If a member violates venue rules, address it immediately — losing
|
||||
a venue relationship hurts the whole community.
|
||||
|
||||
---
|
||||
|
||||
## 6. Handling Sensitive Situations
|
||||
|
||||
### 6.1 A member reports harassment
|
||||
|
||||
1. Thank them for reporting — never dismiss or minimize.
|
||||
2. Ask for screenshots, timestamps, and any witnesses.
|
||||
3. Do not reveal the reporter's identity to the accused.
|
||||
4. Investigate promptly (within 24 hours).
|
||||
5. Take action based on the tier system.
|
||||
6. Follow up with the reporter to let them know the outcome (without
|
||||
sharing details of any punishment).
|
||||
|
||||
### 6.2 A member is in crisis (self-harm, suicidal ideation)
|
||||
|
||||
1. Do not ignore it. Do not dismiss it as attention-seeking.
|
||||
2. Respond with empathy: "I hear you. I care about you. Can I help
|
||||
you find support?"
|
||||
3. Share the 988 Suicide and Crisis Lifeline: **call or text 988**.
|
||||
4. If you believe there is immediate danger, contact local emergency
|
||||
services (911).
|
||||
5. Notify the webmaster privately.
|
||||
6. Do not share the member's situation publicly or with other members.
|
||||
|
||||
### 6.3 A minor is involved
|
||||
|
||||
1. Any content involving a minor that is sexual, exploitative, or
|
||||
predatory is an **immediate Tier 4 permanent ban** on all
|
||||
platforms.
|
||||
2. Preserve all evidence (screenshots with timestamps).
|
||||
3. Contact the webmaster and Moko Consulting immediately.
|
||||
4. If the content may be illegal (CSAM, grooming), report to the
|
||||
National Center for Missing & Exploited Children (NCMEC) at
|
||||
CyberTipline.org and contact local law enforcement.
|
||||
5. Do not attempt to investigate yourself — let authorities handle it.
|
||||
|
||||
---
|
||||
|
||||
### 6.4 Content takedown or privacy request
|
||||
|
||||
If someone requests removal of content that identifies them (photos,
|
||||
real name, personal info):
|
||||
|
||||
1. Take the request seriously regardless of who posted the content.
|
||||
2. Remove or edit the content within 24 hours.
|
||||
3. If the content has cross-posted to Discord/Telegram/Facebook,
|
||||
delete those posts manually.
|
||||
4. Notify the original poster that the content was removed and why.
|
||||
5. No formal moderation action is needed against the poster unless
|
||||
the content was posted maliciously (doxxing — Tier 4).
|
||||
|
||||
### 6.5 Handling media or public attention
|
||||
|
||||
If CF receives press coverage, goes viral, or gets attention from
|
||||
outside the community:
|
||||
|
||||
1. Do not respond to journalists or media on behalf of CF without
|
||||
webmaster approval.
|
||||
2. Do not engage with trolls or bad-faith actors on social media.
|
||||
Ignore, mute, or block.
|
||||
3. If the attention is negative, consider temporarily setting Discord
|
||||
to slow mode and enabling Facebook post approval.
|
||||
4. Coordinate any official response through the webmaster.
|
||||
5. Document the situation for the team so everyone is on the same page.
|
||||
|
||||
---
|
||||
|
||||
## 7. Reporting to Authorities
|
||||
|
||||
If a moderation situation involves potential criminal activity:
|
||||
|
||||
1. **Do not delete the evidence.** Screenshot everything with
|
||||
timestamps and usernames.
|
||||
2. **Do not confront the individual** — this may cause them to
|
||||
destroy evidence or flee.
|
||||
3. Contact local law enforcement (Clarksville Police Department
|
||||
non-emergency: 931-648-0656) or 911 if there is immediate danger.
|
||||
4. For online exploitation of minors, file a report at
|
||||
CyberTipline.org (National Center for Missing & Exploited
|
||||
Children).
|
||||
5. Notify the webmaster and Moko Consulting.
|
||||
|
||||
---
|
||||
|
||||
## 8. Appeals Process
|
||||
|
||||
### 8.1 Who can appeal
|
||||
|
||||
Any member who receives a Tier 2 warning, Tier 3 temporary ban, or
|
||||
Tier 4 permanent ban may appeal. Tier 1 reminders are informal and
|
||||
not appealable.
|
||||
|
||||
### 8.2 How to appeal
|
||||
|
||||
1. The member contacts the webmaster via the Contact Us page at
|
||||
clarksvillefurs.com/contact-us (or by email if they are banned
|
||||
from the website).
|
||||
2. The appeal must include: what happened (their perspective), why
|
||||
they believe the action was incorrect or disproportionate, and
|
||||
what they would do differently.
|
||||
|
||||
### 8.3 Review process
|
||||
|
||||
1. The webmaster reviews the appeal against the moderation log.
|
||||
2. If the original moderator is available, get their input — but the
|
||||
webmaster makes the final call.
|
||||
3. Possible outcomes:
|
||||
- **Upheld** — the original action stands. Explain why.
|
||||
- **Modified** — reduce the severity (e.g., Tier 3 → Tier 2).
|
||||
Update the moderation log.
|
||||
- **Overturned** — remove the action entirely. Apologize if
|
||||
appropriate. Update the moderation log.
|
||||
4. Respond to the member within 7 days.
|
||||
5. Appeals are final. There is no second appeal.
|
||||
|
||||
### 8.4 Exceptions
|
||||
|
||||
Tier 4 bans for threats, CSAM, or predatory behavior toward minors
|
||||
are **not appealable**. These are safety decisions, not judgment calls.
|
||||
|
||||
---
|
||||
|
||||
## 9. Ban Evasion
|
||||
|
||||
### 9.1 Identifying alt accounts
|
||||
|
||||
Signs that a banned member has returned with a new account:
|
||||
|
||||
- New account created shortly after a ban
|
||||
- Same writing style, vocabulary, or topics
|
||||
- Same city/state in Community Builder profile
|
||||
- References to events or conversations the new account shouldn't
|
||||
know about
|
||||
- Other members report recognizing the person
|
||||
|
||||
### 9.2 Handling confirmed evasion
|
||||
|
||||
1. Ban the alt account immediately on all platforms.
|
||||
2. Log it as a new Tier 4 entry referencing the original ban.
|
||||
3. Do not engage in debate about whether it's really them.
|
||||
4. If evasion is persistent (3+ attempts), consider IP-based
|
||||
restrictions on Discord and website registration.
|
||||
|
||||
---
|
||||
|
||||
## 10. Moderator Onboarding
|
||||
|
||||
### 10.1 Checklist for new moderators
|
||||
|
||||
When adding a new Content Moderator:
|
||||
|
||||
- [ ] Add to the **Content Moderators** Joomla user group
|
||||
- [ ] Grant Discord moderator role
|
||||
- [ ] Grant Telegram admin rights in the main chat group
|
||||
- [ ] Grant Facebook group moderator role
|
||||
- [ ] Share access to the moderation log
|
||||
- [ ] Walk through this SOP document — especially Sections 3 (tiers),
|
||||
5 (in-person), and 6 (sensitive situations)
|
||||
- [ ] Introduce them to the mod team in the private moderator channel
|
||||
- [ ] Pair them with an experienced moderator for their first 2 weeks
|
||||
|
||||
### 10.2 Moderator expectations
|
||||
|
||||
- Check in on at least one platform daily (even just a glance)
|
||||
- Respond to reported issues within 24 hours
|
||||
- Log all Tier 2+ actions
|
||||
- Attend mod team check-ins (monthly or as scheduled)
|
||||
- Ask for help when unsure — there's no penalty for escalating
|
||||
|
||||
### 10.3 Removing a moderator
|
||||
|
||||
If a moderator steps down or is removed:
|
||||
|
||||
1. Remove from Content Moderators Joomla group (revokes admin access).
|
||||
2. Remove moderator roles on Discord, Telegram, and Facebook.
|
||||
3. Revoke access to the moderation log.
|
||||
4. Thank them for their service (if voluntary departure).
|
||||
|
||||
---
|
||||
|
||||
## 11. Moderation Log
|
||||
|
||||
All Tier 2+ actions must be logged. Use a shared document or
|
||||
spreadsheet accessible to all moderators.
|
||||
|
||||
Each entry should include:
|
||||
|
||||
| Field | Description |
|
||||
|---|---|
|
||||
| Date | Date and time of the incident |
|
||||
| Platform | Discord, Telegram, Facebook, Website |
|
||||
| Member | Username or display name |
|
||||
| Incident | Brief description of what happened |
|
||||
| Rule violated | Which community guideline was broken |
|
||||
| Tier | 2, 3, or 4 |
|
||||
| Action taken | Warning, mute, temp ban (duration), permanent ban |
|
||||
| Moderator | Who handled it |
|
||||
| Notes | Context, screenshots reference, follow-up needed |
|
||||
|
||||
---
|
||||
|
||||
## 12. Moderator Self-Care
|
||||
|
||||
Moderation is emotionally taxing. Take care of yourself:
|
||||
|
||||
- **You are not on call 24/7.** If something can wait until tomorrow,
|
||||
let it wait. Mute the channel and come back fresh.
|
||||
- **Tag-team difficult situations.** Don't handle a Tier 3 or 4
|
||||
alone — loop in another moderator.
|
||||
- **Step away if you're angry.** You'll make better decisions calm.
|
||||
Mute the conversation, take a walk, come back.
|
||||
- **Debrief after hard incidents.** Talk to a fellow moderator or the
|
||||
webmaster. You shouldn't carry it alone.
|
||||
- **It's okay to ask for help.** If a situation is beyond your
|
||||
experience, escalate to the webmaster or Moko Consulting.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | SOP |
|
||||
| Domain | Community Moderation |
|
||||
| Applies To | Moderators, Content Moderators, Webmaster |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/sop-moderation.md |
|
||||
| Version | 00.02.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-05-01 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-05-01 | Claude | Expanded: in-person events, appeals, ban evasion, onboarding, privacy/takedown, media handling | Sections 5, 6.4–6.5, 8–10 added; renumbered |
|
||||
| 2026-04-27 | Claude | Initial creation | 4-tier system, platform procedures, crisis handling, mod log, self-care |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,441 @@
|
||||
← [Home](Home)
|
||||
|
||||
# SOP — Website Management
|
||||
|
||||
Standard operating procedures for the webmaster and authorized managers
|
||||
of the Clarksville Furs website (clarksvillefurs.com).
|
||||
|
||||
---
|
||||
|
||||
## 1. User Account Management
|
||||
|
||||
### 1.1 Creating a new user account
|
||||
|
||||
1. Log in to the Joomla admin at `clarksvillefurs.com/administrator`.
|
||||
2. Go to **Users > Manage > + New**.
|
||||
3. Fill in: name, username, email, and a temporary password.
|
||||
4. Assign the user to the appropriate group(s):
|
||||
- **Registered** — can log in and view member-only content
|
||||
- **Event Authors** — can create and auto-publish DPCalendar events,
|
||||
edit their own. Cannot post News or edit protected categories
|
||||
(FAQ, About Us, Legal, SOP).
|
||||
- **Content Moderators** — inherits Event Authors permissions, plus:
|
||||
can edit all articles, can access the Joomla admin panel, can
|
||||
manage content across all unlocked categories.
|
||||
- **Manager** — full content control including News, FAQ, About Us,
|
||||
Legal, and SOP categories. Admin panel access.
|
||||
5. Set **Require Password Reset** to Yes.
|
||||
6. Click **Save & Close**.
|
||||
7. Notify the user via the Contact Us system — never send credentials
|
||||
by Discord, Telegram, or any public channel.
|
||||
|
||||
### 1.2 Enabling 2FA for a user
|
||||
|
||||
1. The user logs in for the first time with their temporary password.
|
||||
2. They are prompted to set a new password.
|
||||
3. Go to **Users > Manage** and open the user's profile.
|
||||
4. Under **Multi-factor Authentication**, enable **Authenticator App**.
|
||||
5. The user scans the QR code with their authenticator app and enters
|
||||
the verification code.
|
||||
|
||||
### 1.3 Disabling or removing a user
|
||||
|
||||
1. Go to **Users > Manage** and find the user.
|
||||
2. To temporarily disable: set **Block User** to Yes. The account
|
||||
remains but cannot log in.
|
||||
3. To permanently remove: click the user, then **Delete**. This
|
||||
removes the account but preserves any articles they created.
|
||||
|
||||
### 1.4 Community Builder registration approval
|
||||
|
||||
New registrations through Community Builder require manual approval.
|
||||
|
||||
1. Check the **User Approval Queue** in the Staff Menu.
|
||||
2. Review the registration: name, email, location, birthday.
|
||||
3. Approve legitimate registrations. Reject obvious spam (gibberish
|
||||
names, throwaway emails, empty profiles).
|
||||
4. Approved users receive a welcome email automatically.
|
||||
|
||||
---
|
||||
|
||||
## 2. Content Management
|
||||
|
||||
### 2.1 Publishing an article
|
||||
|
||||
See the [Quick Reference](quick-reference) for the step-by-step
|
||||
workflow.
|
||||
|
||||
### 2.2 Reviewing published content
|
||||
|
||||
Event Authors can auto-publish DPCalendar events. Content Moderators
|
||||
and Managers should periodically review recently published content:
|
||||
|
||||
1. Go to **Content > Articles** or **Components > DPCalendar > Events**
|
||||
and sort by most recent.
|
||||
2. Review for:
|
||||
- Accurate date, time, and location (in the body, not the intro)
|
||||
- Intro text is a teaser that drives traffic to the website
|
||||
- Intro image is set with alt text
|
||||
- No personal contact info (emails, phone numbers)
|
||||
- Tone matches the [Style Guide](style-guide)
|
||||
3. If changes are needed, edit directly or contact the author.
|
||||
4. If content violates Community Guidelines, unpublish immediately
|
||||
and follow the [Moderation SOP](sop-moderation).
|
||||
|
||||
### 2.3 Who can post where
|
||||
|
||||
| Category | Event Authors | Content Mods | Manager+ |
|
||||
|---|---|---|---|
|
||||
| DPCalendar events | Create + publish + edit own | Edit all | Full |
|
||||
| News | No access | No access | Full |
|
||||
| FAQ | No access | No access | Full |
|
||||
| About Us | No access | No access | Full |
|
||||
| Legal | No access | No access | Full |
|
||||
| SOP | No access | No access | Full |
|
||||
|
||||
News articles are authored by Managers only to maintain editorial
|
||||
control over official announcements.
|
||||
|
||||
### 2.4 Editing an existing article
|
||||
|
||||
1. Go to **Content > Articles** and find the article.
|
||||
2. Click the title to open the editor.
|
||||
3. Make changes and click **Save & Close**.
|
||||
4. **Important**: If the article has already cross-posted to Discord,
|
||||
the Discord embed will NOT update. Telegram and Facebook link
|
||||
previews can be refreshed using their respective cache-clearing
|
||||
tools (see [Cross-Post Preview](cross-post-preview)).
|
||||
|
||||
### 2.5 Unpublishing or removing an article
|
||||
|
||||
1. To hide temporarily: set **Status** to **Unpublished**. The article
|
||||
stays in the database but is not visible on the site.
|
||||
2. To remove permanently: set **Status** to **Trashed**, then go to
|
||||
**Content > Articles**, filter by **Trashed**, select, and
|
||||
**Empty Trash**.
|
||||
3. Cross-posts on Discord, Telegram, and Facebook are NOT automatically
|
||||
removed — delete those manually if needed.
|
||||
|
||||
### 2.6 Managing the FAQ
|
||||
|
||||
FAQ articles are in the **FAQ** category (ID: 31). To add a new FAQ:
|
||||
|
||||
1. Create a new article in the FAQ category.
|
||||
2. Write a standalone intro paragraph that fully answers the question
|
||||
(see [Style Guide — Body length targets](style-guide)).
|
||||
3. Add a readmore break after the intro.
|
||||
4. Add detailed content below the break.
|
||||
5. Set the **Ordering** to place it in the right position on the FAQ
|
||||
page (see the current order by viewing the article list sorted by
|
||||
ordering).
|
||||
|
||||
---
|
||||
|
||||
## 3. Events (DPCalendar)
|
||||
|
||||
### 3.1 Creating an event
|
||||
|
||||
Events on the website use the DPCalendar component, not standard
|
||||
articles.
|
||||
|
||||
1. Go to **Components > DPCalendar > Events > + New**.
|
||||
2. Fill in: title, start date/time, end date/time, location, and
|
||||
description.
|
||||
3. Set the calendar (category) and access level.
|
||||
4. Add an image if available.
|
||||
5. Click **Save & Close**.
|
||||
|
||||
### 3.2 Member event submissions
|
||||
|
||||
Members with the **Event Authors** group can submit and auto-publish
|
||||
events from the frontend at `clarksvillefurs.com/events/submit`.
|
||||
|
||||
Events go live immediately — no approval step. Content Moderators and
|
||||
Managers should review recently published events periodically (see
|
||||
Section 2.2).
|
||||
|
||||
If an event needs to be taken down, a Content Moderator or Manager
|
||||
can unpublish it from the admin panel.
|
||||
|
||||
### 3.3 Recurring events
|
||||
|
||||
For monthly meetups or regular events:
|
||||
|
||||
1. Use DPCalendar's **Recurrence** feature.
|
||||
2. Set the recurrence pattern (e.g., first Saturday of every month).
|
||||
3. Individual occurrences can be edited without affecting the series.
|
||||
|
||||
---
|
||||
|
||||
## 4. Cross-Post Management
|
||||
|
||||
### 4.1 How cross-posting works
|
||||
|
||||
Two integrations automatically share content to social channels:
|
||||
|
||||
| Integration | Destination | Trigger |
|
||||
|---|---|---|
|
||||
| MokoDiscordHook | #server-announcements | `onContentAfterSave` for configured categories |
|
||||
| Perfect Publisher | Facebook group + @ClarksvilleFurs Telegram | Rule Engine on category match |
|
||||
|
||||
### 4.2 Verifying a cross-post
|
||||
|
||||
After publishing an article or event:
|
||||
|
||||
1. Wait 1–2 minutes for the integrations to fire.
|
||||
2. Check #server-announcements in Discord for the embed.
|
||||
3. Check @ClarksvilleFurs on Telegram for the message + link preview.
|
||||
4. Check the Facebook group for the post + link card.
|
||||
5. If any cross-post is missing, check that the article's category
|
||||
matches the configured trigger categories.
|
||||
|
||||
### 4.3 Troubleshooting cross-posts
|
||||
|
||||
| Symptom | Likely cause | Fix |
|
||||
|---|---|---|
|
||||
| No Discord embed | Article saved in wrong category, or webhook URL expired | Verify category in article. Check MokoDiscordHook plugin settings for valid webhook URL. |
|
||||
| Discord embed has wrong image | Intro Image not set, or cached | Set Intro Image in the article's Images tab. Discord caches aggressively — the image on the first post is permanent. |
|
||||
| No Telegram message | Perfect Publisher rule not matching, or bot token expired | Check Rule Engine rules. Verify bot is still a member of the channel. |
|
||||
| Telegram preview shows old image | Telegram caches link previews | Use [@webpagebot](https://t.me/webpagebot) to clear cache for the URL. |
|
||||
| No Facebook post | Page token expired, or Rule Engine rule disabled | Re-authenticate the Facebook Page in Perfect Publisher. Check Rule Engine. |
|
||||
| Facebook card shows wrong image | Facebook caches og:image | Use the [Facebook Sharing Debugger](https://developers.facebook.com/tools/debug/) to re-scrape the URL. |
|
||||
|
||||
### 4.4 What cross-posts cannot do
|
||||
|
||||
- Cross-posts do **not** update if you edit the article after
|
||||
publishing. The Discord embed is permanent. Telegram and Facebook
|
||||
can be refreshed via cache-clearing tools, but the original post
|
||||
text does not change.
|
||||
- Cross-posts do **not** auto-delete if you unpublish or trash the
|
||||
article. Delete the Discord message, Telegram message, and Facebook
|
||||
post manually.
|
||||
- Cross-posts show the **intro text only**, not the full article body.
|
||||
Write the intro as a teaser (see
|
||||
[Style Guide](./style-guide.md#body-length-targets)).
|
||||
|
||||
---
|
||||
|
||||
## 5. Community Builder Management
|
||||
|
||||
### 5.1 Required registration fields
|
||||
|
||||
New registrations require: first name, last name, username, email,
|
||||
password, city, state, zip code, country, and birthday.
|
||||
|
||||
### 5.2 Profile moderation
|
||||
|
||||
Periodically review Community Builder profiles for:
|
||||
|
||||
- Inappropriate profile images or avatars
|
||||
- Offensive usernames or display names
|
||||
- Spam or promotional content in profile bio fields
|
||||
- Fake or clearly fabricated profile information
|
||||
|
||||
To edit a profile: go to **Components > Community Builder > User
|
||||
Management**, find the user, click to edit.
|
||||
|
||||
### 5.3 Managing profile fields
|
||||
|
||||
To add, remove, or change required fields:
|
||||
|
||||
1. Go to **Components > Community Builder > Field Management**.
|
||||
2. Find the field by name.
|
||||
3. To make a field required: set **Required** to Yes.
|
||||
4. To show on registration: set **Registration** to Yes.
|
||||
5. To show on profile: set **Profile** to the desired visibility.
|
||||
|
||||
Current required fields: first name, last name, username, email,
|
||||
password, city, state, zip code, country, birthday.
|
||||
|
||||
---
|
||||
|
||||
## 6. Menu Management
|
||||
|
||||
### 6.1 Menu structure
|
||||
|
||||
| Menu | Purpose | Audience |
|
||||
|---|---|---|
|
||||
| Main Menu | Primary site navigation | Everyone |
|
||||
| User Menu | Login, logout, SOPs | Registered users |
|
||||
| Legal Menu | Terms, Privacy, Community Guidelines | Footer links |
|
||||
| Staff Menu | Profile, events, drafts, approvals | Staff/moderators |
|
||||
|
||||
### 6.2 Adding a menu item
|
||||
|
||||
1. Go to **Menus > [Menu Name] > + New**.
|
||||
2. Set the **Menu Item Type** (Single Article, Category Blog, URL, etc.).
|
||||
3. Set the **Title** and **Alias** (alias becomes the URL slug).
|
||||
4. Set **Access** to control who sees the menu item (Public, Registered,
|
||||
Content Moderators, etc.).
|
||||
5. Set **Parent Item** to control nesting.
|
||||
6. Click **Save & Close**.
|
||||
|
||||
### 6.3 Reordering menu items
|
||||
|
||||
1. Go to **Menus > [Menu Name]**.
|
||||
2. Click the ordering column header to enable drag-and-drop.
|
||||
3. Drag items to the desired position.
|
||||
4. Changes take effect immediately — no save needed.
|
||||
|
||||
---
|
||||
|
||||
## 7. Media Management
|
||||
|
||||
### 7.1 Uploading images
|
||||
|
||||
1. Go to **Content > Media** or use the inline media picker in the
|
||||
article editor.
|
||||
2. Organize images into folders: `events/`, `news/`, `branding/`.
|
||||
3. Image requirements:
|
||||
- Format: JPG for photos, PNG for graphics
|
||||
- Intro images: 1200 x 630 px, under 500 KB
|
||||
- Always fill in alt text
|
||||
4. Do not upload images with personally identifiable information
|
||||
(license plates, addresses, faces of minors without consent).
|
||||
|
||||
### 7.2 Cleaning up unused media
|
||||
|
||||
Periodically review the Media Manager for orphaned files:
|
||||
|
||||
1. Go to **Content > Media**.
|
||||
2. Sort by date and review old uploads.
|
||||
3. Before deleting, search for the filename in article content to
|
||||
confirm it is not in use.
|
||||
|
||||
---
|
||||
|
||||
## 8. Backups and Maintenance
|
||||
|
||||
### 8.1 Automated backups
|
||||
|
||||
The site is backed up daily by the hosting provider. Retention:
|
||||
daily for 30 days, weekly for 90 days, monthly for 12 months.
|
||||
|
||||
### 8.2 Cache clearing
|
||||
|
||||
After any significant content change:
|
||||
|
||||
1. Go to **System > Maintenance > Clear Cache**.
|
||||
2. Check all boxes and click **Clear Cache**.
|
||||
3. Go to **System > Maintenance > Purge Expired Cache**.
|
||||
|
||||
### 8.3 Updates
|
||||
|
||||
Joomla core, template, and extension updates are managed by Moko
|
||||
Consulting. Do not install updates without coordination.
|
||||
|
||||
### 8.4 Scheduled maintenance checklist
|
||||
|
||||
**Weekly:**
|
||||
|
||||
- [ ] Review Community Builder approval queue — approve or reject
|
||||
pending registrations
|
||||
- [ ] Check recently published events for accuracy and guideline
|
||||
compliance
|
||||
- [ ] Glance at the moderation log for patterns
|
||||
|
||||
**Monthly:**
|
||||
|
||||
- [ ] Review Media Manager for orphaned or oversized files
|
||||
- [ ] Check cross-post integrations are still firing (publish a test
|
||||
event, verify all three surfaces, then unpublish)
|
||||
- [ ] Review user accounts — block any that haven't logged in for
|
||||
12+ months if desired, or remove obvious spam accounts
|
||||
- [ ] Clear Joomla cache (**System > Maintenance > Clear Cache**)
|
||||
|
||||
**Quarterly:**
|
||||
|
||||
- [ ] Review FAQ articles — are answers still accurate? Any new
|
||||
questions coming up repeatedly in Discord?
|
||||
- [ ] Review SOP articles — do they still match current permissions
|
||||
and workflows?
|
||||
- [ ] Check that 2FA is enabled for all Content Moderators and Managers
|
||||
- [ ] Verify automated backups are running (check backup logs with
|
||||
Moko Consulting)
|
||||
- [ ] Review Community Builder required fields — are they still
|
||||
appropriate?
|
||||
|
||||
---
|
||||
|
||||
## 9. Analytics and Reporting
|
||||
|
||||
### 9.1 What to check
|
||||
|
||||
If analytics are configured (Google Analytics or Tag Manager):
|
||||
|
||||
- **Pageviews**: Which pages get the most traffic? FAQ and Events
|
||||
should be near the top.
|
||||
- **Referral sources**: Are cross-posts driving traffic from Discord,
|
||||
Telegram, and Facebook?
|
||||
- **Search terms**: What are people searching for on the site? Use
|
||||
this to identify missing FAQ articles.
|
||||
- **Bounce rate on Events**: If people land on the events page and
|
||||
leave immediately, the event descriptions may need improvement.
|
||||
|
||||
### 9.2 Reporting cadence
|
||||
|
||||
- **Monthly**: Glance at top pages and referral sources. No formal
|
||||
report needed — just awareness.
|
||||
- **Quarterly**: Share a brief summary with the team: top 5 pages,
|
||||
where traffic comes from, any FAQ gaps identified.
|
||||
|
||||
---
|
||||
|
||||
## 10. Emergency Procedures
|
||||
|
||||
### 10.1 Site is down
|
||||
|
||||
1. Check if the issue is local (try a different browser/device/network).
|
||||
2. Check the hosting provider's status page.
|
||||
3. Contact Moko Consulting via the Contact Us system or the emergency
|
||||
contact in the onboarding documentation.
|
||||
4. Do not attempt server-level fixes unless you have been trained.
|
||||
|
||||
### 10.2 Security incident (defacement, unauthorized access)
|
||||
|
||||
1. Do not make changes to the site — preserve evidence.
|
||||
2. Contact Moko Consulting immediately.
|
||||
3. If you have admin access, check **Users > Manage** for unfamiliar
|
||||
accounts.
|
||||
4. Change your own password immediately from a trusted device.
|
||||
|
||||
### 10.3 Spam or inappropriate content
|
||||
|
||||
1. Unpublish the content immediately.
|
||||
2. Block the user account if applicable.
|
||||
3. Document the incident (screenshot, user details, timestamp).
|
||||
4. Report to Moko Consulting if the spam came through an automated
|
||||
vector (registration exploit, comment spam).
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | SOP |
|
||||
| Domain | Website Management |
|
||||
| Applies To | Webmaster, Content Moderators |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/sop-website-management.md |
|
||||
| Version | 00.02.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-05-01 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-05-01 | Claude | Expanded: cross-posts, CB profiles, menus, analytics, maintenance checklist | Sections 4–6, 8.4, 9 added; permissions updated for auto-publish model |
|
||||
| 2026-04-27 | Claude | Initial creation | User management, content, events, media, backups, emergencies |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,178 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Style Guide — Events and News
|
||||
|
||||
Rules for writing articles that sound like Clarksville Furs and look
|
||||
good across every surface (website, Discord, Telegram, Facebook).
|
||||
|
||||
## Voice and tone
|
||||
|
||||
Clarksville Furs articles should feel like a friend inviting you to
|
||||
hang out — not a corporation issuing a press release.
|
||||
|
||||
**Be:**
|
||||
|
||||
- **Warm** — "We'd love to see you there" over "Attendance is
|
||||
encouraged."
|
||||
- **Direct** — short sentences, plain words. Say what's happening,
|
||||
when, and where.
|
||||
- **Inclusive** — write for everyone: newcomers, families, kids, people
|
||||
who've never heard of the fandom. No inside jokes that leave readers
|
||||
out.
|
||||
- **Casual** — contractions are fine. "We're" not "We are." First
|
||||
person plural ("we", "our") for the group.
|
||||
- **Enthusiastic but not over-the-top** — one exclamation mark per
|
||||
article is plenty. Let the event speak for itself.
|
||||
|
||||
**Don't be:**
|
||||
|
||||
- Corporate — no "leverage", "synergy", "stakeholders", "action items."
|
||||
- Vague — "sometime in June" is not a date. Use `TBA` if it's truly
|
||||
unknown (see below).
|
||||
- Edgy — keep it family-friendly. No profanity, no sarcasm that could
|
||||
land wrong.
|
||||
|
||||
## Title format
|
||||
|
||||
Use this pattern for event titles:
|
||||
|
||||
```
|
||||
Event Name — Location
|
||||
```
|
||||
|
||||
Examples:
|
||||
|
||||
- `Monthly Meetup — Downtown Clarksville`
|
||||
- `Barnaby TN Ren Fest — Triune, TN`
|
||||
- `Movie Night — TBA`
|
||||
|
||||
For news articles, just use a clear descriptive title:
|
||||
|
||||
- `We're Live: Introducing Our New Website`
|
||||
- `Summer Schedule Update`
|
||||
|
||||
Rules:
|
||||
|
||||
- Use an em dash ( — ) between event name and location, not a hyphen.
|
||||
- Title-case the event name.
|
||||
- Keep it under 70 characters so it doesn't truncate in Discord embeds.
|
||||
- Don't put the date in the title — it's in the publish date and the
|
||||
body.
|
||||
|
||||
## Body length targets
|
||||
|
||||
| Article type | Target length | Notes |
|
||||
|---|---|---|
|
||||
| Event listing | 50–150 words | Date, time, location, what to expect, how to RSVP |
|
||||
| News post | 100–300 words | What happened or is changing, why it matters, what's next |
|
||||
| Longer feature | 300–600 words | Only when the topic genuinely needs it |
|
||||
|
||||
The first 1–2 sentences are the **intro**. This text appears in
|
||||
cross-posts and category listings. Write the intro as a **teaser** that
|
||||
hooks the reader and drives them to the full event page on the website
|
||||
— do not put the full date, time, and location in the intro. Save
|
||||
those details for the article body so people click through to
|
||||
clarksvillefurs.com/events to get the complete picture.
|
||||
|
||||
## Image specs
|
||||
|
||||
Every Events article should have an **Intro Image** set. This image
|
||||
appears in:
|
||||
|
||||
- The category list view on the website
|
||||
- Discord embeds (via MokoDiscordHook)
|
||||
- Facebook link cards (via Perfect Publisher)
|
||||
- Telegram link previews (via Perfect Publisher)
|
||||
|
||||
| Property | Requirement |
|
||||
|---|---|
|
||||
| Format | JPG or PNG (JPG preferred for photos) |
|
||||
| Dimensions | 1200 x 630 px (landscape, 1.91:1 ratio) |
|
||||
| File size | Under 500 KB |
|
||||
| Alt text | Required. Describe what's in the image, not the event title. Example: "Furries in costume at a park picnic table" |
|
||||
|
||||
Tips:
|
||||
|
||||
- Avoid text overlaid on the image — it gets cropped differently on
|
||||
each platform.
|
||||
- Use a photo of the venue, the group, or the activity. Generic stock
|
||||
images feel impersonal.
|
||||
- If you don't have a photo, use the CF mascot image from the Media
|
||||
Manager rather than leaving it blank.
|
||||
|
||||
## Using TBA for unknown details
|
||||
|
||||
If the date, time, or location isn't confirmed yet, use `TBA`
|
||||
(To Be Announced) as a placeholder:
|
||||
|
||||
- **Date unknown:** Set the publish date to today and write "Date: TBA"
|
||||
in the body. Update the article when the date is confirmed.
|
||||
- **Location unknown:** Use `TBA` in the title where the location goes:
|
||||
`Monthly Meetup — TBA`
|
||||
- **Time unknown:** Write "Time: TBA" in the body.
|
||||
|
||||
Always go back and update TBA fields before the event. A stale TBA
|
||||
looks like nobody's running things.
|
||||
|
||||
## Recurring events
|
||||
|
||||
For recurring events (monthly meetups, weekly game nights):
|
||||
|
||||
- Create a **new article** for each occurrence. Don't edit the old one.
|
||||
- Use a consistent title pattern: `Monthly Meetup — Downtown Clarksville`
|
||||
(same name each time, location may change).
|
||||
- In the body, reference that this is a recurring event:
|
||||
"Our monthly meetup is back! This month we're at..."
|
||||
- Set the **Start Publishing** date to a few days before the event so
|
||||
it shows up in the listing with lead time.
|
||||
|
||||
## What NOT to do
|
||||
|
||||
- **Don't use HTML in the article body** unless you're using an
|
||||
approved utility class (see
|
||||
[Content Authoring Guide](content-authoring)). The editor's
|
||||
visual mode handles formatting.
|
||||
- **Don't hardcode brand colors** inline — use `.cf-brand-accent` or
|
||||
`.cf-brand-callout` instead. See the
|
||||
[Content Authoring Guide](../content-authoring.md#patterns-to-avoid).
|
||||
- **Don't leave Alt Text blank** on images. Screen readers need it, and
|
||||
social platforms use it as fallback text.
|
||||
- **Don't write a novel.** If your event listing is over 200 words,
|
||||
you're probably over-explaining. Trust the reader.
|
||||
- **Don't duplicate the title in the first sentence.** The title is
|
||||
already displayed above the body.
|
||||
- **Don't use all caps** for emphasis. Bold a word if you must.
|
||||
- **Don't link to personal social media accounts** — only official CF
|
||||
channels.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | guide |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Event Authors group, Webmaster |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/authoring/style-guide.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | Phase 3 voice, title, image, and formatting rules |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,158 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Brand Reference — Clarksville Furs
|
||||
|
||||
## Core palette
|
||||
|
||||
Nine tokens. Every color on the site should trace back to one of these.
|
||||
|
||||
| Token | Hex | Role |
|
||||
|---|---|---|
|
||||
| Sky Primary | `#9CCEDB` | Large surfaces, hero washes, block-color-1 |
|
||||
| Sky Secondary | `#7FB7C6` | Gradient depth, light-mode `--color-primary`, bottom-a container |
|
||||
| Sky Raw (`--sky`) | `#a3cde2` | Module tints, `.custom.sky` cards, top-b container background |
|
||||
| Coral Accent | `#FF4B3E` | CTAs, links, focus, `.btn-primary`, brand-accent text |
|
||||
| Ink Outline | `#1E1E1E` | Body text, linework, light-mode navigation background |
|
||||
| Mascot White | `#F4F4F4` | Soft surfaces, on-dark button text |
|
||||
| Mascot Grey | `#8F8F8F` | Muted text, secondary neutral |
|
||||
| Gold Eye | `#F5C518` | Highlights, warning states, `.custom.yellow` cards |
|
||||
| Soft Red | `#ff7a73` | `.btn-danger`, `.custom.red` cards — softer than coral, semantic danger |
|
||||
|
||||
The Sky Raw token `--sky` is available as a CSS custom property for direct
|
||||
reference in article HTML, module content, and user extensions. Prefer it over
|
||||
hardcoding `#a3cde2`.
|
||||
|
||||
## Typography
|
||||
|
||||
**Primary:** Fredoka (variable weight 300–700). Loaded locally from
|
||||
`/media/templates/site/mokoonyx/fonts/Fredoka-Variable.ttf` via `@font-face` in
|
||||
`user.css`.
|
||||
|
||||
**Secondary:** Nunito (weights 400–700). Loaded from Google Fonts for resilience;
|
||||
bundle locally if performance audits require it.
|
||||
|
||||
**Stack:**
|
||||
|
||||
```css
|
||||
--body-font-family: "Fredoka", "Nunito", "Inter",
|
||||
-apple-system, BlinkMacSystemFont, "Segoe UI", Roboto,
|
||||
"Helvetica Neue", Arial, "Noto Sans", sans-serif;
|
||||
```
|
||||
|
||||
**Weight scale (per brand guide):**
|
||||
|
||||
| Element | Weight | Notes |
|
||||
|---|---|---|
|
||||
| `h1`–`h3`, `.site-title` | 700 | Fredoka, letter-spacing `-0.01em` |
|
||||
| `h4`–`h6` | 600 | Fredoka |
|
||||
| `.lead`, `.callout`, `.subhead` | 500 | Fredoka |
|
||||
| Body (`p`, `li`, `td`, `dd`) | 400 | Nunito falls back to Fredoka |
|
||||
| `small`, `.text-muted`, `.meta` | 300 | Nunito |
|
||||
|
||||
**Note on `.site-title`:** MokoOnyx's base template ships with an "Osaka" font
|
||||
loaded via `fonts/osaka.css`. CF overrides this with `!important` in `user.css`
|
||||
to force Fredoka on site title markers. If the MokoOnyx template is updated and
|
||||
this class changes, the override may need to follow.
|
||||
|
||||
## Design decisions
|
||||
|
||||
These are the non-obvious choices that drive the look and won't survive a naïve
|
||||
"reset to defaults" pass. Read before changing anything in the theme.
|
||||
|
||||
### `--color-primary` is Sky Secondary (#7FB7C6) in light mode, not coral
|
||||
|
||||
MokoOnyx's offline page uses `--color-primary` as a full-viewport background.
|
||||
Coral at that scale would be jarring. Sky-secondary reads warm and on-brand at
|
||||
hero scale. Coral retains its role as the action color via Bootstrap's `--primary`.
|
||||
|
||||
### Navigation is ink in light mode, dark-neutral in dark mode
|
||||
|
||||
Light mode uses `#1E1E1E` ink as nav background with mascot-white text — structural
|
||||
brand presence at the top of every page. Dark mode uses `#151B22` neutral dark so
|
||||
the nav doesn't compete with content for attention. Active link is coral in light,
|
||||
sky in dark.
|
||||
|
||||
### Baseline `--border-radius` is 0.875rem
|
||||
|
||||
Matches the template's own offline-card radius. Gives consistent soft-rounded
|
||||
surfaces across form controls, badges, alerts, dropdowns, popovers, toasts.
|
||||
Cards use a slightly larger 1rem radius; hero cards use 1.25rem.
|
||||
|
||||
### Coral hover on dark-tint cards fails AA
|
||||
|
||||
`.custom.green` cards (`#448344`) keep white text (4.61:1 AA pass) but the
|
||||
coral hover on green links is 1.39:1 — visually invisible. This is documented
|
||||
in-file. If hover legibility becomes a complaint, swap hover to ink.
|
||||
|
||||
### `.custom.red` uses ink text, not white
|
||||
|
||||
White on `#ff7a73` is 2.53:1 (AA fail). Ink is 5.79:1 (AA pass) AND reads
|
||||
warmer, which matches the "Celebrating Individuality" card's intended tone.
|
||||
This is a deliberate departure from the "white on colored card" convention.
|
||||
|
||||
### `--danger` is soft red (#ff7a73), not coral
|
||||
|
||||
Bootstrap expects primary and danger to be distinct colors. Coral owns primary
|
||||
(brand action); soft red owns danger (alarm states). A compatibility rule in
|
||||
`user.css` keeps `.text-danger` on `h1`–`h6` and `.display-*` rendering as coral
|
||||
so existing hero content (which uses `.text-danger` decoratively) still reads as
|
||||
brand-accent. New decorative uses should prefer `.cf-brand-accent`.
|
||||
|
||||
## Accessibility baselines
|
||||
|
||||
All non-incidental text on the live site is checked to at least WCAG AA (4.5:1
|
||||
for normal text, 3:1 for ≥18pt or ≥14pt bold). Known exceptions are documented
|
||||
in [accessibility.md](accessibility).
|
||||
|
||||
**Contrast pairs that pass AA or better:**
|
||||
|
||||
| Foreground | Background | Ratio | Grade |
|
||||
|---|---|---|---|
|
||||
| Ink `#1E1E1E` | White `#FFFFFF` | 15.3:1 | AAA |
|
||||
| Ink `#1E1E1E` | Sky Primary `#9CCEDB` | 10.97:1 | AAA |
|
||||
| Ink `#1E1E1E` | Sky Secondary `#7FB7C6` | 8.22:1 | AAA |
|
||||
| Ink `#1E1E1E` | Sky Raw `#a3cde2` | 12.1:1 | AAA |
|
||||
| Ink `#1E1E1E` | Coral `#FF4B3E` | 5.16:1 | AA |
|
||||
| Ink `#1E1E1E` | Soft Red `#ff7a73` | 5.79:1 | AA |
|
||||
| Ink `#1E1E1E` | Gold `#F5C518` | 11.5:1 | AAA |
|
||||
| White `#F4F4F4` | Ink `#1E1E1E` | 15.3:1 | AAA |
|
||||
| White `#F4F4F4` | Dark Green `#448344` | 4.61:1 | AA |
|
||||
|
||||
**Contrast pairs that fail AA (known, documented, handled):**
|
||||
|
||||
| Foreground | Background | Ratio | Mitigation |
|
||||
|---|---|---|---|
|
||||
| Coral `#FF4B3E` | Sky Primary | 2.33:1 | Scoped override: links on sky containers flip to ink |
|
||||
| Coral `#FF4B3E` | Sky Secondary | 2.06:1 | Scoped override (same) |
|
||||
| Coral `#FF4B3E` | White (small text) | 3.63:1 | Only used for large text / headings (AA-large passes) |
|
||||
| White | Soft Red | 2.53:1 | Not used — `.custom.red` uses ink text instead |
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | reference |
|
||||
| Domain | Brand |
|
||||
| Applies To | All client-clarksvillefurs theme and content work |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/brand-reference.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-21 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-21 | Claude | Initial creation | Synthesized from brand guide + theme work |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,184 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Content Authoring Guide
|
||||
|
||||
This is for whoever writes articles, modules, and page content in the Joomla
|
||||
admin. The CF theme adds a small library of utility classes that make it easy
|
||||
to put on-brand components into articles without touching CSS.
|
||||
|
||||
## Quick lookup: "I want to…"
|
||||
|
||||
| Goal | Use | Example |
|
||||
|---|---|---|
|
||||
| Add a warm welcome/community box | `.cf-brand-callout` | See below |
|
||||
| Make heading text pop coral | `.cf-brand-accent` | `<span class="cf-brand-accent">Your place.</span>` |
|
||||
| Tint a feature card sky blue | `.custom.sky` wrapper on a `.card` | See below |
|
||||
| Tint a feature card red/yellow/green | `.custom.red` / `.custom.yellow` / `.custom.green` | See below |
|
||||
| Heavy sticker outline around any box | `.cf-sticker` | See below |
|
||||
|
||||
## `.cf-brand-callout` — welcome and community boxes
|
||||
|
||||
Use for the "💙 Clarksville Furs is an all-ages, family-friendly community"
|
||||
pattern on the FAQ page and similar. Handles the sky background, ink text,
|
||||
readable link color (ink with coral hover), and flex layout for an icon +
|
||||
paragraph.
|
||||
|
||||
```html
|
||||
<div class="cf-brand-callout">
|
||||
<span class="fs-5">💙</span>
|
||||
<p class="mb-0 small">
|
||||
<strong>Clarksville Furs is an all-ages, family-friendly community.</strong>
|
||||
Find us on <a href="/discord">Discord</a>,
|
||||
<a href="/telegram">Telegram</a>, and
|
||||
<a href="https://facebook.com/clarksvillefurs">Facebook</a>.
|
||||
</p>
|
||||
</div>
|
||||
```
|
||||
|
||||
**Do not** author this as inline `<div style="background: var(--color-primary)">`.
|
||||
The utility class handles the contrast scoping automatically — the inline
|
||||
pattern is legacy and currently works via a selector hack in `user.css` but
|
||||
should be migrated.
|
||||
|
||||
## `.cf-brand-accent` — coral brand-pop text
|
||||
|
||||
For the "pop of coral" on big headings that used to be done with `.text-danger`.
|
||||
|
||||
```html
|
||||
<h1 class="display-4 fw-bold">
|
||||
<span class="cf-brand-accent">Your place.</span> Your pack.
|
||||
</h1>
|
||||
```
|
||||
|
||||
`.text-danger` on h1–h6 and `.display-*` still renders as coral via a
|
||||
compatibility rule, so existing content doesn't break — but `.cf-brand-accent`
|
||||
is semantically correct and should be used for all new content.
|
||||
|
||||
## `.custom.{sky|red|yellow|green}` — tinted feature cards
|
||||
|
||||
Wrap a standard Bootstrap `.card` in a `.mod-custom.custom.{color}` module
|
||||
wrapper (or any div with `custom.{color}`) to paint it with a brand tint. The
|
||||
card-body text color auto-flips for legibility.
|
||||
|
||||
```html
|
||||
<div class="mod-custom custom sky">
|
||||
<div class="card border-0 h-100 rounded-3">
|
||||
<div class="card-body p-4 text-center">
|
||||
<i class="fa-solid fa-house fs-2 mb-3 d-block"></i>
|
||||
<h5 class="card-title fw-bold">Belonging First</h5>
|
||||
<p class="card-text small">
|
||||
Every decision starts with one question: will this make someone
|
||||
feel welcome?
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
```
|
||||
|
||||
Tint → text-color mapping:
|
||||
|
||||
| Class | Card bg | Card body text | AA on body |
|
||||
|---|---|---|---|
|
||||
| `.custom.sky` | `#a3cde2` | Ink (black) | 12.1:1 AAA |
|
||||
| `.custom.red` | `#ff7a73` | Ink (black) | 5.79:1 AA |
|
||||
| `.custom.yellow` | `#ffd166` | Ink (black) | 13.3:1 AAA |
|
||||
| `.custom.green` | `#448344` | White | 4.61:1 AA |
|
||||
|
||||
Links inside these cards are auto-styled:
|
||||
|
||||
- `.custom.sky`, `.custom.red`, `.custom.yellow` — ink links, coral hover
|
||||
- `.custom.green` — white links, coral hover (hover contrast is low — don't
|
||||
rely on hover color alone to indicate interactivity)
|
||||
|
||||
## `.cf-sticker` — heavy-outline sticker aesthetic
|
||||
|
||||
Opt-in mascot-inspired look: thick outline and hard-offset shadow that lifts on
|
||||
hover. Use sparingly, for feature callouts and stickers where the brand
|
||||
personality should shout.
|
||||
|
||||
```html
|
||||
<div class="cf-sticker p-4 bg-white">
|
||||
<h3>Meet-up this Saturday</h3>
|
||||
<p>Join us at the park — bring snacks, bring friends.</p>
|
||||
</div>
|
||||
```
|
||||
|
||||
## Patterns to avoid
|
||||
|
||||
### Inline hex colors for brand colors
|
||||
|
||||
```html
|
||||
<span style="color: #FF4B3E;">Your place.</span>
|
||||
|
||||
<span class="cf-brand-accent">Your place.</span>
|
||||
```
|
||||
|
||||
Hardcoded hexes don't update when the theme does. If the brand ever shifts
|
||||
(new accent color, tonal correction), utility classes update site-wide in a
|
||||
single CSS change.
|
||||
|
||||
### Inline `style="background: var(--color-primary)"`
|
||||
|
||||
Currently works because `user.css` has a scoped override, but it's fragile.
|
||||
Prefer `.cf-brand-callout` for callout boxes.
|
||||
|
||||
### White-on-coral text
|
||||
|
||||
```html
|
||||
<a href="..." style="background: #FF4B3E; color: white;">Join us</a>
|
||||
|
||||
<a href="..." class="btn btn-primary">Join us</a>
|
||||
```
|
||||
|
||||
The `.btn-primary` class handles the ink-on-coral contrast correctly. Don't
|
||||
re-invent it inline.
|
||||
|
||||
### Hardcoded brand colors that fail contrast
|
||||
|
||||
The home page currently has a Telegram CTA with `style="background: #26A5E4;
|
||||
color: #fff;"` — white on Telegram's official light cyan measures 2.44:1, fails
|
||||
AA. Either use ink text (`color: #1E1E1E`, 5.09:1 AA) or switch to Telegram's
|
||||
darker brand variant `#0088CC`.
|
||||
|
||||
## Common edits that need a content pass
|
||||
|
||||
When any of these come up in an editor review, expect to fix content, not CSS:
|
||||
|
||||
- **Placeholder URLs** like `/YOUR_FACEBOOK_URL`, `YOUR_DISCORD_INVITE_URL`,
|
||||
`YOUR_TELEGRAM_URL` — real URLs are `/discord` and `/telegram` (server-side
|
||||
redirects). Facebook needs a real URL or the mention should be removed.
|
||||
- **Hardcoded brand-color CTAs** without contrast audit — Discord `#5865F2`
|
||||
with white text is fine (4.50:1), Telegram `#26A5E4` fails.
|
||||
- **Decorative `.text-danger`** on body text — only on headings does the
|
||||
compatibility rule keep it coral. On body text it renders as soft red
|
||||
(correctly, semantically), which may not be the author's intent.
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | guide |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | All Joomla article editors working on the CF site |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/content-authoring.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-21 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-21 | Claude | Initial creation | Covers v02.06.00 theme utility classes |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# CSS Variables Reference
|
||||
|
||||
Quick reference for the CSS custom properties that drive the CF theme. The full
|
||||
theme files (`light.custom.css` and `dark.custom.css`) declare 924+ variables
|
||||
each, but most are Bootstrap internals that inherit from the tokens below. Edit
|
||||
the tokens, not the internals.
|
||||
|
||||
Base template: [MokoOnyx](https://github.com/mokoconsulting-tech/MokoCassiopeia)
|
||||
(formerly MokoCassiopeia).
|
||||
|
||||
---
|
||||
|
||||
## Brand tokens
|
||||
|
||||
These are the raw CF brand values. Every other variable in the theme should
|
||||
trace back to one of these.
|
||||
|
||||
| Token | Variable | Light | Dark | Notes |
|
||||
|---|---|---|---|---|
|
||||
| Sky Primary | `--accent-color-secondary` (light) / `--color-primary` (dark) | `#9CCEDB` | `#9CCEDB` | Hero washes, large surfaces |
|
||||
| Sky Secondary | `--color-primary` (light) / `--accent-color-secondary` (dark) | `#7FB7C6` | `#7FB7C6` | Gradient depth, offline page bg |
|
||||
| Sky Raw | `--sky` | `#a3cde2` | `#a3cde2` | Module tints, `.custom.sky` cards |
|
||||
| Coral | `--accent-color-primary` | `#FF4B3E` | `#FF4B3E` | CTAs, links, focus rings |
|
||||
| Ink | `--body-color` (light) | `#1E1E1E` | n/a | Body text, linework |
|
||||
| Mascot White | `--white` | `#F4F4F4` | `#F4F4F4` | Soft surfaces, on-dark text |
|
||||
| Mascot Grey | `--muted-color` | `#8F8F8F` | `#8F8F8F` | Secondary text |
|
||||
| Gold | `--yellow` | `#F5C518` | `#F5C518` | Highlights, warnings |
|
||||
| Soft Red | `--danger` | `#ff7a73` | `#ff7a73` | Danger states |
|
||||
|
||||
**Key light/dark swap:** `--color-primary` is Sky Secondary in light mode but
|
||||
Sky Primary in dark mode. This is intentional — see
|
||||
[brand-reference.md](./brand-reference.md#--color-primary-is-sky-secondary-7fb7c6-in-light-mode-not-coral)
|
||||
for the reasoning.
|
||||
|
||||
---
|
||||
|
||||
## Bootstrap palette mapping
|
||||
|
||||
CF brand tokens mapped to Bootstrap's contextual color system. These drive
|
||||
`.btn-*`, `.bg-*`, `.text-*`, `.border-*`, `.alert-*`, and `.badge-*` utilities.
|
||||
|
||||
| Bootstrap semantic | Light value | Dark value | CF token |
|
||||
|---|---|---|---|
|
||||
| `--primary` | `#FF4B3E` (Coral) | `#FF4B3E` | Coral Accent |
|
||||
| `--secondary` | `#8F8F8F` (Mascot Grey) | `#8F8F8F` | Mascot Grey |
|
||||
| `--success` | `#4AA664` | `#4AA664` | -- (standard green) |
|
||||
| `--info` | `#7FB7C6` (Sky Secondary) | `#7FB7C6` | Sky Secondary |
|
||||
| `--warning` | `#F5C518` (Gold) | `#F5C518` | Gold Eye |
|
||||
| `--danger` | `#ff7a73` (Soft Red) | `#ff7a73` | Soft Red |
|
||||
| `--light` | `#F4F4F4` (Mascot White) | `#F4F4F4` | Mascot White |
|
||||
| `--dark` | `#1E1E1E` (Ink) | `#1E1E1E` | Ink Outline |
|
||||
|
||||
**Note:** `--primary` is Coral (the action color), not Sky. `--info` is Sky
|
||||
Secondary. This is deliberate — Coral is the CTA/interaction color across the
|
||||
site; Sky is the ambient brand surface.
|
||||
|
||||
---
|
||||
|
||||
## Dark mode color strategy
|
||||
|
||||
The theme supports full light/dark mode switching. Key differences:
|
||||
|
||||
| Property | Light | Dark | Why |
|
||||
|---|---|---|---|
|
||||
| `--color-primary` | `#7FB7C6` (Sky Secondary) | `#9CCEDB` (Sky Primary) | Lighter sky reads better against dark backgrounds |
|
||||
| `--body-color` | `#1E1E1E` (Ink) | `#E6EBF1` (Light gray) | Ink is the text color in light; light gray in dark |
|
||||
| `--body-bg` | `#FFFFFF` | `#0E1318` (Near-black) | |
|
||||
| `--heading-color` | `#1E1E1E` | `#F4F4F4` (Mascot White) | |
|
||||
| `--nav-bg-color` | `#1E1E1E` (Ink) | `#151B22` (Dark neutral) | Ink nav is structural in light; neutral in dark so nav doesn't compete with content |
|
||||
| `--navbar-active-color` | `#FF4B3E` (Coral) | `#FF4B3E` (Coral) | Same — coral stays the active indicator |
|
||||
| `--link-color` | `#FF4B3E` (Coral) | `#FF4B3E` (Coral) | Same — coral links in both modes |
|
||||
| `--link-hover-color` | `#E03828` (Darker coral) | `#E03828` | Same |
|
||||
| `--code-color` | `#FF4B3E` | `#FF7A6F` (Lighter coral) | Softer in dark for readability |
|
||||
| `--secondary-bg` | `#F4F4F4` | `#151B22` | Card backgrounds, dropdowns |
|
||||
| `--card-bg` | `#F4F4F4` (via `--secondary-bg`) | `#151B22` | |
|
||||
| `--border-color` | `#D6D6D6` | `#2b323b` | |
|
||||
|
||||
The `--sky` token is mode-invariant (`#a3cde2` in both). This means
|
||||
`.custom.sky` cards and `--sky`-based surfaces look the same regardless of
|
||||
mode — the surrounding page contrast changes, not the card itself.
|
||||
|
||||
---
|
||||
|
||||
## Typography variables
|
||||
|
||||
Typography is mode-invariant — defined once in the theme files and reinforced
|
||||
by `user.css`.
|
||||
|
||||
| Variable | Value | Notes |
|
||||
|---|---|---|
|
||||
| `--body-font-family` | `'Fredoka', 'Nunito', -apple-system, ...` | Full stack in both theme files + `user.css` |
|
||||
| `--body-font-size` | `1rem` | |
|
||||
| `--body-font-weight` | `400` | Nunito for body text |
|
||||
| `--body-line-height` | `1.5` | |
|
||||
| `--font-monospace` | `SFMono-Regular, Menlo, Monaco, ...` | Standard monospace stack |
|
||||
|
||||
Weight hierarchy is enforced by `user.css`, not the theme files — see
|
||||
[brand-reference.md](./brand-reference.md#typography).
|
||||
|
||||
---
|
||||
|
||||
## Border & radius
|
||||
|
||||
| Variable | Value | Notes |
|
||||
|---|---|---|
|
||||
| `--border-radius` | `0.875rem` | Baseline for all CF components |
|
||||
| `--border-radius-sm` | `0.5rem` | Badges, small controls |
|
||||
| `--border-radius-lg` | `1.25rem` | Hero cards |
|
||||
| `--border-radius-xl` | `1.5rem` | |
|
||||
| `--border-radius-pill` | `50rem` | Fully rounded (pills, FABs) |
|
||||
| `--card-border-radius` | `1rem` | Cards slightly larger than baseline |
|
||||
| `--border-color` | `#D6D6D6` (light) / `#2b323b` (dark) | |
|
||||
|
||||
---
|
||||
|
||||
## Container color map
|
||||
|
||||
MokoOnyx defines several page-region containers. These are the CF color
|
||||
assignments:
|
||||
|
||||
| Container | Light bg | Dark bg | Notes |
|
||||
|---|---|---|---|
|
||||
| Header | `light_skybackground.png` | (image) | Background image, not a flat color |
|
||||
| Below Topbar | `#F4F4F4` (Mascot White) | `#151B22` | Soft neutral strip |
|
||||
| Top A | `none` (transparent) | `none` | Inherits page bg |
|
||||
| Top B | `var(--sky)` = `#a3cde2` | `var(--sky)` | Sky-tinted — triggers contrast overrides |
|
||||
| TOC | `var(--secondary-bg)` | `var(--secondary-bg)` | Sidebar table of contents |
|
||||
| Sidebar | `#F4F4F4` | `#151B22` | 0.75rem radius |
|
||||
| Bottom A | `#7FB7C6` (Sky Secondary) | varies | Sky-tinted — triggers contrast overrides |
|
||||
| Bottom B | `#1E1E1E` (Ink) | `#0E1318` | Dark strip, typically footer area |
|
||||
|
||||
**Contrast implications:** Top B and Bottom A use sky backgrounds, which means
|
||||
links inside them are automatically flipped to ink via the scoped override in
|
||||
`user.css`. See [accessibility.md](./accessibility.md#coral-on-sky-links-fail-aa--fixed).
|
||||
|
||||
---
|
||||
|
||||
## Button variants
|
||||
|
||||
All buttons use ink (`#1E1E1E`) text for AA contrast. The `.btn-dark` variant
|
||||
uses Mascot White text instead.
|
||||
|
||||
### Solid buttons
|
||||
|
||||
| Class | Background | Hover bg | CF token |
|
||||
|---|---|---|---|
|
||||
| `.btn-primary` | `#FF4B3E` (Coral) | `#FF6B60` | Coral Accent |
|
||||
| `.btn-secondary` | `#9CCEDB` (Sky Primary) | `#7FB7C6` | Sky Primary |
|
||||
| `.btn-success` | `#78D694` | `#9CE3B2` | -- |
|
||||
| `.btn-info` | `#9CCEDB` (Sky Primary) | `#7FB7C6` | Sky Primary |
|
||||
| `.btn-warning` | `#F5C518` (Gold) | `#FFD84A` | Gold Eye |
|
||||
| `.btn-danger` | `#ff7a73` (Soft Red) | `#e5615a` | Soft Red |
|
||||
| `.btn-light` | `#F4F4F4` (Mascot White) | `#FFFFFF` | Mascot White |
|
||||
| `.btn-dark` | `#1E1E1E` (Ink) | `#333333` | Ink Outline |
|
||||
|
||||
### Outline buttons
|
||||
|
||||
Outline variants use the brand color as text/border color and fill on hover:
|
||||
|
||||
| Class | Text/border | Hover fill |
|
||||
|---|---|---|
|
||||
| `.btn-outline-primary` | Coral `#FF4B3E` | Coral |
|
||||
| `.btn-outline-secondary` | Sky `#9CCEDB` | Sky |
|
||||
| `.btn-outline-success` | `#78D694` | Green |
|
||||
| `.btn-outline-info` | Sky `#9CCEDB` | Sky |
|
||||
| `.btn-outline-warning` | Gold `#F5C518` | Gold |
|
||||
| `.btn-outline-danger` | `#c0453e` | Soft Red |
|
||||
| `.btn-outline-light` | Mascot White | Mascot White |
|
||||
| `.btn-outline-dark` | `#B8C3CB` | `#B8C3CB` |
|
||||
|
||||
All solid buttons have `--btn-border-color: #1E1E1E` (ink outline) for the
|
||||
sticker/outlined aesthetic. Outline buttons swap to ink border on hover.
|
||||
|
||||
---
|
||||
|
||||
## Hero system
|
||||
|
||||
Two hero variants for banner sections:
|
||||
|
||||
| Variant | Background | Overlay | Text color |
|
||||
|---|---|---|---|
|
||||
| Primary | Sky Primary `#9CCEDB` | 55% sky gradient | Ink `#1E1E1E` |
|
||||
| Secondary | Ink `#1E1E1E` | 78% ink overlay | Mascot White `#F4F4F4` |
|
||||
|
||||
Hero card dimensions: `max-width: 800px`, `padding: 3rem 2rem`,
|
||||
`border-radius: 1.25rem`. Alt card is narrower at `600px`.
|
||||
|
||||
---
|
||||
|
||||
## Block colors
|
||||
|
||||
Used for module position color rotation (top-a, top-b, bottom-a, bottom-b):
|
||||
|
||||
| Block | Background | Text | Typical use |
|
||||
|---|---|---|---|
|
||||
| Block 1 | `var(--secondary-bg)` | `var(--body-color)` | Neutral modules |
|
||||
| Block 2 | Coral `#FF4B3E` | Mascot White | CTA modules |
|
||||
| Block 3 | Gold `#F5C518` | Gold | Highlight modules |
|
||||
| Block 4 | Mascot White `#F4F4F4` | Sky Primary | Light modules |
|
||||
|
||||
Additional block overrides:
|
||||
|
||||
| Variable | Value | Use |
|
||||
|---|---|---|
|
||||
| `--block-highlight-bg` | Gold 18% opacity | Subtle gold wash |
|
||||
| `--block-cta-bg` | Coral solid | Call-to-action blocks |
|
||||
| `--block-alert-bg` | Coral 18% opacity | Alert/notice blocks |
|
||||
|
||||
---
|
||||
|
||||
## Editing guidelines
|
||||
|
||||
1. **Edit brand tokens, not internals.** If you need to change a color, find
|
||||
the brand token it maps to and change that. The 900+ downstream variables
|
||||
inherit automatically.
|
||||
|
||||
2. **Edit in both theme files.** Every color change in `light.custom.css`
|
||||
likely needs a corresponding change in `dark.custom.css`.
|
||||
|
||||
3. **Run a contrast audit** after any color change. See
|
||||
[accessibility.md](./accessibility.md#audit-tools) for tools.
|
||||
|
||||
4. **Bump the file version** in the header comment on every edit.
|
||||
|
||||
5. **Clear Joomla cache** after deploying — see
|
||||
[deployment.md](deployment) for the full workflow.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | reference |
|
||||
| Domain | CSS Variables |
|
||||
| Applies To | All CSS changes in light.custom.css, dark.custom.css, user.css |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/css-variables.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-22 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-22 | Claude | Initial creation | Replaces deleted CSS_VARIABLES.md with focused reference |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,180 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Deployment
|
||||
|
||||
## Environments
|
||||
|
||||
| Environment | URL | Purpose |
|
||||
|---|---|---|
|
||||
| Development | `clarksvillefurs.dev.mokoconsulting.tech` | Moko internal staging — first stop for all changes |
|
||||
| Production | `clarksvillefurs.com` | Live site |
|
||||
|
||||
Development mirrors production's Joomla version, template, extensions, and
|
||||
data. Testing on dev first is required for every theme change.
|
||||
|
||||
## Theme package deliverables
|
||||
|
||||
A theme-only deploy consists of three CSS files and, if changed, the font file:
|
||||
|
||||
```
|
||||
deploy/
|
||||
├── images/
|
||||
│ └── branding/
|
||||
│ ├── logo_full_wide.png
|
||||
│ ├── mascot.png
|
||||
│ └── web_logo_full_wide.png
|
||||
└── media/
|
||||
└── templates/
|
||||
└── site/
|
||||
└── mokoonyx/
|
||||
├── css/
|
||||
│ ├── theme/
|
||||
│ │ ├── light.custom.css
|
||||
│ │ └── dark.custom.css
|
||||
│ └── user.css
|
||||
└── fonts/
|
||||
└── Fredoka-Variable.ttf
|
||||
```
|
||||
|
||||
## SFTP deployment (manual, current process)
|
||||
|
||||
Copy SFTP credentials from `docs/templates/sftp-config.json.template` into a
|
||||
local, gitignored `sftp-config.json`. Connect via any SFTP client (Transmit,
|
||||
FileZilla, Cyberduck, rsync over ssh).
|
||||
|
||||
**Upload paths** (relative to Joomla web root):
|
||||
|
||||
- `/media/templates/site/mokoonyx/css/theme/light.custom.css`
|
||||
- `/media/templates/site/mokoonyx/css/theme/dark.custom.css`
|
||||
- `/media/templates/site/mokoonyx/css/user.css`
|
||||
- `/media/templates/site/mokoonyx/fonts/Fredoka-Variable.ttf` *(only if font file changed)*
|
||||
- `/images/branding/*.png` *(only if images changed)*
|
||||
|
||||
**Note:** The template directory on the server may still be
|
||||
`/media/templates/site/mokocassiopeia/` if the MokoCassiopeia → MokoOnyx rename
|
||||
has not yet been completed on that environment. Check the actual directory
|
||||
name with `ls` on the server; the *file contents* reference `mokoonyx` in
|
||||
their headers regardless of the current folder name, which is correct
|
||||
forward-looking metadata.
|
||||
|
||||
## Cache busting after deploy
|
||||
|
||||
Joomla caches heavily. After uploading CSS, always:
|
||||
|
||||
1. Joomla admin → **System → Maintenance → Clear Cache** → check all boxes → Clear Cache
|
||||
2. Joomla admin → **System → Maintenance → Purge Expired Cache**
|
||||
3. Verify cache-bust query string on the CSS URL changed (e.g. `?475b76` → new hash)
|
||||
|
||||
If the query string didn't change, the template file mod-times weren't
|
||||
picked up. Touching any file in the template directory (e.g. via SFTP `touch`
|
||||
or re-saving the template in admin) forces a regeneration.
|
||||
|
||||
Hard-refresh the browser (Ctrl+Shift+R / Cmd+Shift+R) to bypass local cache.
|
||||
|
||||
## Verification checklist
|
||||
|
||||
On the dev environment, after every deploy:
|
||||
|
||||
1. Home page loads without console errors
|
||||
2. Light mode renders as expected (sky header PNG, ink nav, coral CTAs)
|
||||
3. Dark mode toggle works — CSS vars all resolve, no broken fallbacks
|
||||
4. Hero "Your place." renders as coral (not washed pink) in light mode
|
||||
5. `.custom.{sky,red,yellow,green}` cards render with correct tints and readable text
|
||||
6. FAQ page blue callout at top — links are ink, not coral
|
||||
7. Footer / `.container-bottom-a` — sky-secondary bg, ink text, link overrides working
|
||||
8. No FOUC on Fredoka font load (font-display: swap handles this)
|
||||
9. Contrast spot-checks on any new text/bg pair using browser DevTools
|
||||
|
||||
If any check fails, roll back (reupload previous version) before promoting
|
||||
to production.
|
||||
|
||||
## Automated dev → live sync (daily cron)
|
||||
|
||||
Dev and live share the same database, so only the filesystem needs syncing.
|
||||
A cron job on the dev server runs `rsync` daily at **3:00 AM server time** to
|
||||
push filesystem changes to live.
|
||||
|
||||
### How it works
|
||||
|
||||
| Component | Location (dev server) |
|
||||
|---|---|
|
||||
| Script | `/home/clarksvillefurs/scripts/sync-dev-to-live.sh` |
|
||||
| SSH key | `~/.ssh/id_sync_to_live` (ed25519, authorized on live) |
|
||||
| Cron entry | `0 3 * * * /home/clarksvillefurs/scripts/sync-dev-to-live.sh` |
|
||||
| Log file | `/home/clarksvillefurs/scripts/logs/sync-dev-to-live.log` |
|
||||
|
||||
The script uses `rsync -avz --delete` with excludes for environment-specific
|
||||
files (`configuration.php`, `.htaccess`, `cache/`, `tmp/`, `logs/`,
|
||||
dev-only files, DreamHost system files). It includes a PID-based lock file
|
||||
to prevent overlapping runs.
|
||||
|
||||
### Manual run
|
||||
|
||||
SSH into the dev server and execute directly:
|
||||
|
||||
```bash
|
||||
/home/clarksvillefurs/scripts/sync-dev-to-live.sh
|
||||
cat /home/clarksvillefurs/scripts/logs/sync-dev-to-live.log
|
||||
```
|
||||
|
||||
### Updating the script
|
||||
|
||||
The canonical copy lives in the repo at `scripts/sync-dev-to-live.sh`.
|
||||
After editing, SCP it to the dev server:
|
||||
|
||||
```bash
|
||||
scp scripts/sync-dev-to-live.sh clarksvillefurs@dev.mokoconsulting.tech:/home/clarksvillefurs/scripts/
|
||||
ssh clarksvillefurs@dev.mokoconsulting.tech "sed -i 's/\r$//' /home/clarksvillefurs/scripts/sync-dev-to-live.sh"
|
||||
```
|
||||
|
||||
The `sed` command strips Windows line endings (required for bash execution).
|
||||
|
||||
## Production promotion (manual)
|
||||
|
||||
Only after full dev verification:
|
||||
|
||||
1. Upload the same files to production SFTP (or wait for the next automated sync at 3 AM)
|
||||
2. Run the same cache-clear sequence in production Joomla admin
|
||||
3. Verify the same checklist in an incognito window against the production URL
|
||||
4. Tag the git commit with the release version (`git tag v02.06.00 && git push --tags`)
|
||||
|
||||
## Rollback
|
||||
|
||||
Keep the previous working version of each CSS file in `/deploy/archive/vXX.YY.ZZ/`
|
||||
before uploading. If production starts throwing errors or visibly breaks:
|
||||
|
||||
1. SFTP upload the previous version back into place
|
||||
2. Clear caches
|
||||
3. Verify the rollback worked
|
||||
4. Root-cause the failure on dev before re-attempting
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | guide |
|
||||
| Domain | DevOps |
|
||||
| Applies To | All theme and template deployments |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/deployment.md |
|
||||
| Version | 00.02.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Added automated dev→live sync section | Cron rsync workflow, script reference, manual run instructions |
|
||||
| 2026-04-21 | Claude | Initial creation | SFTP workflow, cache-busting, rollback |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,248 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Migration Plan — Events and News
|
||||
|
||||
End-to-end plan for enabling Clarksville Furs managers to author event
|
||||
listings and news posts that automatically cross-post to Discord,
|
||||
Telegram, and Facebook.
|
||||
|
||||
## Goal
|
||||
|
||||
Give the **Event Authors** Joomla group a self-service workflow:
|
||||
create an article in the Events or News category, attach an image,
|
||||
publish — and have the post appear on all CF social channels within
|
||||
minutes, with no webmaster intervention.
|
||||
|
||||
## Stakeholders
|
||||
|
||||
| Role | Responsibility |
|
||||
|---|---|
|
||||
| Moko Consulting | Technical implementation, plugin configuration, documentation, training |
|
||||
| Webmaster | Account provisioning, 2FA setup, day-to-day oversight |
|
||||
| Event Authors | Article creation and publishing |
|
||||
|
||||
---
|
||||
|
||||
## Phase 1 — Infrastructure
|
||||
|
||||
Set up the Joomla categories, user group, and plugin wiring.
|
||||
|
||||
### 1.1 Create content categories
|
||||
|
||||
- [ ] **Events** category under `com_content` (published, public access)
|
||||
- [ ] **News** category under `com_content` (published, public access)
|
||||
— News (ID: 16) already exists; verify description and alias
|
||||
|
||||
### 1.2 Create the Event Authors user group
|
||||
|
||||
- [ ] Create Joomla user group **Event Authors** (child of Registered)
|
||||
- [ ] Grant article-create and article-edit-own permissions on the
|
||||
Events and News categories
|
||||
- [ ] Deny publish permission — articles default to Unpublished until
|
||||
a moderator (or the webmaster) approves, unless the author also
|
||||
holds a higher group
|
||||
- [ ] Assign initial members
|
||||
|
||||
### 1.3 Configure MokoDiscordHook
|
||||
|
||||
MokoDiscordHook fires `onContentAfterSave` and sends a Discord embed.
|
||||
|
||||
- [ ] Install / verify MokoDiscordHook plugin is enabled
|
||||
- [ ] Set the target Discord webhook URL for #server-announcements
|
||||
- [ ] Configure category trigger: Events category ID, News category ID
|
||||
- [ ] Embed fields mapped:
|
||||
- **Title** ← article title
|
||||
- **Description** ← article intro text
|
||||
- **Image** ← intro image URL
|
||||
- **Link** ← full article URL on clarksvillefurs.com
|
||||
|
||||
### 1.4 Configure Perfect Publisher
|
||||
|
||||
Perfect Publisher posts to Facebook and Telegram via the Rule Engine.
|
||||
|
||||
- [ ] Install / verify Perfect Publisher is enabled
|
||||
- [ ] Connect Facebook group (clarksvillefurs) — verify Page token is valid
|
||||
- [ ] Connect Telegram channel (@ClarksvilleFurs) — verify
|
||||
bot token and channel membership
|
||||
- [ ] Create Rule Engine rules:
|
||||
- **Rule: Events → FB + Telegram** — category match on Events,
|
||||
action = publish to FB Page + Telegram channel
|
||||
- **Rule: News → FB + Telegram** — category match on News,
|
||||
action = publish to FB Page + Telegram channel
|
||||
- [ ] Post content mapped:
|
||||
- **Facebook**: intro text as post body, article URL as link
|
||||
(link card pulls `og:title`, `og:image`, `og:description`)
|
||||
- **Telegram**: intro text + article URL as message body
|
||||
(link preview pulls from Open Graph meta tags)
|
||||
|
||||
### 1.5 Verify Open Graph tags
|
||||
|
||||
- [ ] Confirm Joomla outputs `og:title`, `og:description`, `og:image`
|
||||
for articles (MokoOnyx or a plugin handles this)
|
||||
- [ ] Test with Facebook Sharing Debugger and Telegram @webpagebot
|
||||
|
||||
---
|
||||
|
||||
## Phase 2 — Dry run
|
||||
|
||||
Validate the full pipeline end-to-end before handing off to authors.
|
||||
|
||||
### 2.1 Test article pipeline
|
||||
|
||||
- [ ] Create a test article in the Events category with:
|
||||
- Title following style guide format: `Test Event — Downtown Clarksville`
|
||||
- 1–2 sentence intro text
|
||||
- Intro image (1200x630 JPG, with alt text)
|
||||
- Publish date set to now
|
||||
- Status = Published
|
||||
- [ ] Verify article appears on the website Events listing
|
||||
- [ ] Verify Discord embed arrives in #server-announcements
|
||||
- Title, description, image, link all correct
|
||||
- [ ] Verify Telegram message arrives in @ClarksvilleFurs
|
||||
- Message text, link preview card all correct
|
||||
- [ ] Verify Facebook post appears on clarksvillefurs group
|
||||
- Post text, link card image and title all correct
|
||||
- [ ] Repeat for a News category article
|
||||
- [ ] Delete or unpublish test articles after verification
|
||||
|
||||
### 2.2 Test author permissions
|
||||
|
||||
- [ ] Log in as an Event Authors member (not a super admin)
|
||||
- [ ] Confirm the user can create articles in Events and News
|
||||
- [ ] Confirm the user cannot edit other users' articles
|
||||
- [ ] Confirm the user cannot access admin areas beyond Content
|
||||
|
||||
### 2.3 Test edge cases
|
||||
|
||||
- [ ] Article with no intro image — cross-posts should still work
|
||||
(no image in embed, but no error)
|
||||
- [ ] Article with a very long title (70+ characters) — check
|
||||
truncation on Discord embed
|
||||
- [ ] Article saved as Unpublished — cross-posts should NOT fire
|
||||
- [ ] Article edited after publishing — Discord embed does NOT update
|
||||
(expected; document this for authors)
|
||||
|
||||
---
|
||||
|
||||
## Phase 3 — Documentation and training
|
||||
|
||||
Author the manager-facing documentation and record the walkthrough.
|
||||
|
||||
### 3.1 Authoring documentation
|
||||
|
||||
All files live under `docs/authoring/`. See the
|
||||
[Authoring Documentation Index](authoring-README) for the full
|
||||
list and reading order.
|
||||
|
||||
| Document | Purpose |
|
||||
|---|---|
|
||||
| [README](authoring-README) | Index, audience, reading order |
|
||||
| [Quick Reference](authoring-quick-reference) | One-page cheat sheet — log in through publish |
|
||||
| [Style Guide](authoring-style-guide) | Voice, tone, title format, image specs, don'ts |
|
||||
| [Cross-Post Preview](authoring-cross-post-preview) | Field-to-surface mapping with worked example |
|
||||
| [Screencast Script](authoring-screencast-script) | 8-scene spoken script for the walkthrough recording |
|
||||
|
||||
### 3.2 Dry-run checklist for docs
|
||||
|
||||
Each document must have:
|
||||
|
||||
- [ ] Moko HTML-comment file header (Copyright, SPDX, FILE INFORMATION)
|
||||
- [ ] DEFGROUP: `ClarksvilleFurs.Documentation`
|
||||
- [ ] INGROUP: `ClarksvilleFurs`
|
||||
- [ ] VERSION starting at `00.01.00`
|
||||
- [ ] Metadata table and Revision History table at the bottom
|
||||
- [ ] Pure Markdown body — no HTML except the file header
|
||||
- [ ] Placeholder tokens for values TBD:
|
||||
`[LAUNCH DATE]` (the only remaining placeholder)
|
||||
|
||||
### 3.3 Record walkthrough
|
||||
|
||||
- [ ] Record the screencast using the
|
||||
[Screencast Script](authoring-screencast-script)
|
||||
- [ ] Presenter: Moko Consulting
|
||||
- [ ] Runtime target: 5–8 minutes
|
||||
- [ ] Upload to a location accessible to Event Authors (Google Drive,
|
||||
YouTube unlisted, or embedded on the site)
|
||||
- [ ] Link from the authoring README
|
||||
|
||||
### 3.4 Onboard first authors
|
||||
|
||||
- [ ] Schedule a live walkthrough session with initial Event Authors
|
||||
- [ ] Share the authoring docs link
|
||||
- [ ] Have each author create a test article and verify cross-posts
|
||||
- [ ] Collect feedback and update docs as needed
|
||||
|
||||
---
|
||||
|
||||
## Phase 4 — Launch
|
||||
|
||||
Go live and hand off to the team.
|
||||
|
||||
### 4.1 Fill in placeholders
|
||||
|
||||
- [ ] Replace `[LAUNCH DATE]` across all authoring docs
|
||||
- [x] ~~Replace `[CF Discord channel name]`~~ → #server-announcements
|
||||
- [x] ~~Replace `[FB Page ID]`~~ → clarksvillefurs (Facebook group)
|
||||
- [x] ~~Replace `[Telegram channel handle]`~~ → @ClarksvilleFurs
|
||||
- [x] ~~Replace `[Webmaster email]`~~ → Contact Us page (clarksvillefurs.com/contact-us)
|
||||
|
||||
### 4.2 Publish
|
||||
|
||||
- [ ] Merge authoring docs to main branch
|
||||
- [ ] Enable auto-publish permissions for Event Authors (if dry run
|
||||
proved they don't need moderator approval)
|
||||
- [ ] Announce in Discord and Telegram that the Events page is live
|
||||
- [ ] Monitor first 5 real posts for cross-post issues
|
||||
|
||||
### 4.3 Post-launch
|
||||
|
||||
- [ ] Review cross-post analytics after 2 weeks
|
||||
- [ ] Update docs based on author feedback
|
||||
- [ ] Consider adding a menu item for Events on the main navigation
|
||||
(currently hidden: `menu_show=0` on item 457)
|
||||
|
||||
---
|
||||
|
||||
## Constraints
|
||||
|
||||
- **MokoDiscordHook**: embed with title, intro text, image, link.
|
||||
Fires `onContentAfterSave` for configured categories. Does NOT
|
||||
update embeds if the article is edited after initial save.
|
||||
- **Perfect Publisher**: native FB Page post + Telegram channel post,
|
||||
triggered by Rule Engine on category match. Link previews depend
|
||||
on Open Graph meta tags being present and correct.
|
||||
- **No invented features**: this plan only uses capabilities that
|
||||
exist in the installed plugins. If a feature isn't listed here,
|
||||
it doesn't exist.
|
||||
|
||||
---
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | plan |
|
||||
| Domain | Content Authoring |
|
||||
| Applies To | Events and News authoring workflow |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/migration-plan-events.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Draft |
|
||||
| Last Reviewed | 2026-04-26 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-26 | Claude | Initial creation | 4-phase plan: infrastructure, dry run, documentation, launch |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,151 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Theme Architecture
|
||||
|
||||
The CF theme rides on top of MokoOnyx (Joomla 5 template). MokoOnyx provides
|
||||
everything structural (layout, scaffolding, responsive grid, component behavior).
|
||||
CF's theme layer only changes colors, fonts, and introduces a small library of
|
||||
utility classes.
|
||||
|
||||
## File roster
|
||||
|
||||
Three CSS files make up the CF theme layer. They live under the MokoOnyx
|
||||
template directory and survive template updates because MokoOnyx's CSS cascade
|
||||
is ordered to read the `.custom` files after its own `.standard` files.
|
||||
|
||||
```
|
||||
/media/templates/site/mokoonyx/
|
||||
├── css/
|
||||
│ ├── theme/
|
||||
│ │ ├── light.custom.css ← light-mode palette
|
||||
│ │ └── dark.custom.css ← dark-mode palette
|
||||
│ ├── user.css ← persistent overrides (fonts, utilities)
|
||||
│ └── theme/
|
||||
│ ├── light.standard.css ← template default, do NOT edit
|
||||
│ └── dark.standard.css ← template default, do NOT edit
|
||||
└── fonts/
|
||||
└── Fredoka-Variable.ttf ← brand font
|
||||
```
|
||||
|
||||
## Load order
|
||||
|
||||
MokoOnyx loads stylesheets in this order on every page. Later files override
|
||||
earlier files per CSS cascade rules:
|
||||
|
||||
1. `template.base.css` — Bootstrap 5.3 + MokoOnyx layout primitives
|
||||
2. `fonts/osaka.css` — template's default heading font (overridden later)
|
||||
3. `theme/light.standard.css` — Bootstrap palette + MokoOnyx variable defaults
|
||||
4. `theme/dark.standard.css` — same, dark-mode scoped under `:root[data-bs-theme='dark']`
|
||||
5. `theme/light.custom.css` — **CF palette** (this is ours)
|
||||
6. `theme/dark.custom.css` — **CF dark palette** (this is ours)
|
||||
7. `user.css` — **persistent overrides** (this is ours)
|
||||
8. `a11y-high-contrast.css` — accessibility toggle
|
||||
9. `bootstrap.css` — Bootstrap component styles (read vars set above)
|
||||
|
||||
The CF files sit between the template's defaults and Bootstrap's final component
|
||||
pass, so our variable values flow into every Bootstrap component that reads them.
|
||||
|
||||
## What each CF file is allowed to change
|
||||
|
||||
### `light.custom.css` and `dark.custom.css`
|
||||
|
||||
**Purpose:** Full color palette for each theme mode. These files are a
|
||||
comprehensive redeclaration of every MokoOnyx / Bootstrap 5 custom property in
|
||||
the template's scaffold — 684 variables per file at the time of writing.
|
||||
|
||||
**Scope of edits:**
|
||||
|
||||
- All `--color-*` brand tokens
|
||||
- All Bootstrap contextual colors (`--primary`, `--secondary`, `--success`, `--info`, `--warning`, `--danger`, `--light`, `--dark`) and their `-rgb`, `-text-emphasis`, `-bg-subtle`, `-border-subtle` variants
|
||||
- Typography tokens that should vary by mode (none currently — font stack is mode-invariant and lives in `user.css`)
|
||||
- All container backgrounds (`--container-top-a-*`, `--container-top-b-*`, `--container-bottom-a-*`, `--container-bottom-b-*`, `--container-sidebar-*`, `--container-toc-*`, `--container-below-topbar-*`)
|
||||
- Hero variant styling (`--hero-primary-*`, `--hero-secondary-*`, `--hero-card-*`, `--hero-alt-card-*`)
|
||||
- Block color rotation (`--block-color-1` through `-4`, plus overrides)
|
||||
- All Bootstrap component defaults (accordion, alert, badge, breadcrumb, card, dropdown, list-group, modal, nav-tabs, nav-pills, offcanvas, pagination, popover, progress, spinner, table, toast, tooltip)
|
||||
- Button variants (`.btn-primary` through `.btn-dark`, `.btn-outline-*`, `.btn-link`) — live at stylesheet root, not nested, following the MokoOnyx scaffold convention
|
||||
|
||||
**Not in scope:** typography, layout, spacing outside Bootstrap's defaults.
|
||||
Those belong in `user.css`.
|
||||
|
||||
### `user.css`
|
||||
|
||||
**Purpose:** Persistent non-color overrides. Edits here survive template updates
|
||||
and color changes without touching the palette files.
|
||||
|
||||
**Scope of edits:**
|
||||
|
||||
- `@font-face` loading for Fredoka
|
||||
- `@import` for Nunito from Google Fonts
|
||||
- Global font-stack override via `:root { --body-font-family }`
|
||||
- Typography weight hierarchy (per brand guide)
|
||||
- `.site-title` override to beat Osaka
|
||||
- Rounded-corner enforcement on `.form-control`, `.form-select`, `.alert`, `.badge`, `.input-group-text`, `.btn`
|
||||
- `.btn` base sizing (`padding: 0.65rem 1.5rem`) and `.btn-lg` variant
|
||||
- Opt-in utility classes: `.cf-sticker`, `.cf-brand-callout`, `.cf-brand-accent`
|
||||
- Tinted card classes: `.custom.sky`, `.custom.red`, `.custom.yellow`, `.custom.green`
|
||||
- Blue-background contrast override (scoped ink-link treatment inside sky surfaces)
|
||||
- Decorative `.text-danger` → coral compatibility rule for headings
|
||||
- `:focus-visible` accessibility outline
|
||||
- Link underline offset for body text
|
||||
|
||||
## Versioning
|
||||
|
||||
All three files use zero-padded semver in their `FILE INFORMATION` header
|
||||
comment. Version is displayed prominently near the top of each file and must be
|
||||
bumped on every edit.
|
||||
|
||||
Current versions (as of last update):
|
||||
|
||||
| File | Version |
|
||||
|---|---|
|
||||
| `light.custom.css` | 02.04.00 |
|
||||
| `dark.custom.css` | 02.02.00 |
|
||||
| `user.css` | 01.05.00 |
|
||||
|
||||
## Cache busting
|
||||
|
||||
Joomla cache-busts CSS via a query string appended to every asset URL (e.g.
|
||||
`?475b76`). The cache key is regenerated when any template file changes on
|
||||
disk. A deploy should always be followed by a template rebuild (Joomla admin →
|
||||
System → Maintenance → Clear Cache) to make browsers pick up the new version.
|
||||
|
||||
## Safe-edit checklist
|
||||
|
||||
Before committing any CSS change:
|
||||
|
||||
1. Brace balance — count `{` and `}` occurrences, must match
|
||||
2. File version bumped in header comment
|
||||
3. No direct hex usage where a `var(--*)` exists — always prefer the token
|
||||
4. Contrast audit for any color change touching text/background pairs
|
||||
5. Both light and dark mode tested (toggle in the site header)
|
||||
6. File header comment still present and valid
|
||||
|
||||
## Metadata
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| Document Type | reference |
|
||||
| Domain | Theme Architecture |
|
||||
| Applies To | All CSS changes in this repo |
|
||||
| Jurisdiction | Moko Consulting |
|
||||
| Owner | Moko Consulting |
|
||||
| Repo | mokoconsulting-tech/client-clarksvillefurs |
|
||||
| Path | ./docs/theme-architecture.md |
|
||||
| Version | 00.01.00 |
|
||||
| Status | Active |
|
||||
| Last Reviewed | 2026-04-21 |
|
||||
| Reviewed By | Claude |
|
||||
|
||||
## Revision History
|
||||
|
||||
| Date | Author | Change | Notes |
|
||||
|---|---|---|---|
|
||||
| 2026-04-21 | Claude | Initial creation | Based on v02.06.00 theme package |
|
||||
|
||||
---
|
||||
|
||||
*Repo: [client-clarksvillefurs](https://git.mokoconsulting.tech/ClarksvilleFurs/client-waas-clarksvillefurs) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,27 @@
|
||||
# MokoCRM
|
||||
|
||||
White-label CRM platform for Dolibarr ERP
|
||||
|
||||
---
|
||||
|
||||
## Pages
|
||||
|
||||
- [README](README)
|
||||
- [changelog](changelog)
|
||||
- [development](development)
|
||||
- [installation](installation)
|
||||
- [module id policy](module-id-policy)
|
||||
- [roadmap](roadmap)
|
||||
- [update server](update-server)
|
||||
|
||||
---
|
||||
|
||||
**Category:** Dolibarr | **Platform:** [moko-platform wiki](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,144 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoCRM Documentation Index
|
||||
|
||||
Welcome to the MokoCRM documentation. This guide will help you navigate all available documentation resources for the MokoCRM Dolibarr white-label module.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Install and enable MokoCRM
|
||||
- [Development Guide](development.md) - Extend or customise MokoCRM
|
||||
- [Roadmap](roadmap.md) - Planned features and version milestones
|
||||
- [Module ID](module-id-policy.md) - Module ID 185067 details
|
||||
- [Changelog](changelog.md) - Version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For Administrators
|
||||
|
||||
If you're installing MokoCRM on your Dolibarr instance:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Configuration and setup
|
||||
- Troubleshooting common issues
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're extending or contributing to MokoCRM:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and organisation
|
||||
- White label configuration
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
2. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Code standards
|
||||
- Pull request process
|
||||
- Commit message guidelines
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
- **[Module ID](module-id-policy.md)** - Official module ID 185067
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Installation Guide](installation.md) to install MokoCRM, then review the [Development Guide](development.md) if you want to extend it.
|
||||
|
||||
**Q: What is MokoCRM's module ID?**
|
||||
A: MokoCRM uses the officially registered Dolibarr module ID **185067**. See [Module ID](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
**Q: Where are the code examples?**
|
||||
A: The [Development Guide](development.md) contains code examples and best practices.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: [mokoconsulting-tech/MokoCRM](https://github.com/mokoconsulting-tech/MokoCRM/issues)
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
|
||||
### Moko Consulting
|
||||
|
||||
- [MokoConsulting Tech](https://mokoconsulting.tech)
|
||||
- [MokoConsulting Tech GitHub](https://github.com/mokoconsulting-tech)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 185067; // MokoCRM official module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
git clone https://github.com/mokoconsulting-tech/MokoCRM.git mokocrm
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Module Version**: 01.01.00
|
||||
- **Module ID**: 185067
|
||||
- **Last Updated**: 2026-03-19
|
||||
- **Minimum Dolibarr Version**: 19.0
|
||||
- **PHP Version**: 7.1+
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- Installing MokoCRM? Start with the [Installation Guide](installation.md)
|
||||
- Extending MokoCRM? Check out the [Development Guide](development.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,58 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to MokoCRM will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
## [01.02.00] - Unreleased
|
||||
|
||||
### Added
|
||||
- CRM configuration installed automatically on module activation: 37 custom extrafields across 12 Dolibarr objects (`societe`, `socpeople`, `projet`, `propal`, `facture`, `facturedet`, `actioncomm`, `fichinter`, `fichinterdet`, `expensereport`, `expensereport_det`, `facture_fourn`)
|
||||
- Three custom dictionary tables (`llx_moko_commission_rate`, `llx_moko_meeting_time`, `llx_moko_meeting_day`) created and seeded on activation; exposed in the Dolibarr dictionary admin via `$this->dictionaries`
|
||||
- 17 module constants registered via `$this->const` (FICHINTER_* workflow flags, proposal/invoice defaults, PDF options)
|
||||
- Core dictionary data: 3 payment terms, 2 units of measure, 11 expense/fee categories, 6 third-party types, 11 contact roles, 8 opportunity sources, 12 custom activity types, updated lead pipeline stages and prospect qualification levels
|
||||
- 7 branded HTML email templates (proposals, invoices, contract) with Moko Blue (#1A6FD4) header
|
||||
- Notification defaults for `PROPAL_VALIDATE` and `BILL_VALIDATE` to `sales@mokoconsulting.tech`
|
||||
- Payment method additions (ACH, Stripe, Square, Zelle, Venmo Business) and order entry method English relabels
|
||||
- 8 product–client relation types and 20 US business legal forms
|
||||
- Physical extrafield columns added via `information_schema`-safe `ALTER TABLE` helper (idempotent, skips missing tables for optional modules)
|
||||
- Full uninstall: `remove()` deletes all extrafield metadata, drops physical columns, and drops the three custom dictionary tables
|
||||
- Comprehensive lang file (`langs/en_US/mokocrm.lang`) covering all new labels, select options, roles, and activity types
|
||||
|
||||
## [01.01.00] - 2026-03-12
|
||||
|
||||
### Added
|
||||
- Set `MAIN_LOGIN_BACKGROUND` to `access_restricted_banner.png` on module activation and remove it on deactivation using `dolibarr_set_const()` / `dolibarr_del_const()` (`core/lib/admin.lib.php`); `init()` also copies the bundled image to `$conf->mycompany->dir_output/logos/` so Dolibarr can serve it via `viewimage.php?modulepart=mycompany&file=logos/access_restricted_banner.png`
|
||||
- Set `editor_squarred_logo` to `favicon_256.png@mokocrm` for the module card in Dolibarr admin
|
||||
- Dynamic development environment warning toast shown once per browser session via `sessionStorage` when `$this->version === 'development'` (`js/mokocrm.js.php`)
|
||||
- Dynamic `" - Development"` suffix appended to `document.title` on every page when `$this->version === 'development'` (`js/mokocrm.js.php`)
|
||||
|
||||
## [01.00.00] - 2026-03-10
|
||||
|
||||
### Added
|
||||
- Initial MokoCRM Dolibarr module with official module ID **185067**
|
||||
- Module descriptor (`modMokoCRM.class.php`) with white label `overwrite_translation` for `DolibarrProductName` and `Dolibarr` → MokoCRM
|
||||
- English translation file (`langs/en_US/mokocrm.lang`) with MokoCRM-branded keys
|
||||
- Admin setup page (`admin/setup.php`) and about page (`admin/about.php`)
|
||||
- Library file (`lib/mokocrm.lib.php`) with admin navigation helper
|
||||
- Module icon (`img/object_mokostandards.png`)
|
||||
- Comprehensive documentation (installation, development, module ID, changelog)
|
||||
|
||||
---
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/MokoCRM/compare/v01.01.00...HEAD
|
||||
[01.01.00]: https://github.com/mokoconsulting-tech/MokoCRM/compare/v01.00.00...v01.01.00
|
||||
[01.00.00]: https://github.com/mokoconsulting-tech/MokoCRM/releases/tag/v01.00.00
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,404 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing and extending the MokoCRM Dolibarr module.
|
||||
|
||||
## Module Structure
|
||||
|
||||
MokoCRM follows the standard Dolibarr module structure under `src/`:
|
||||
|
||||
```
|
||||
src/ # Module source (deploy as "mokocrm/")
|
||||
├── admin/ # Admin pages
|
||||
│ ├── about.php # About page
|
||||
│ ├── index.php # Directory index
|
||||
│ └── setup.php # Configuration page
|
||||
├── core/
|
||||
│ ├── modules/
|
||||
│ │ └── modMokoCRM.class.php # Module descriptor
|
||||
│ └── substitutions/
|
||||
│ └── functions_mokocrm.lib.php # White label substitution functions
|
||||
├── css/
|
||||
│ └── mokocrm.css.php # White label CSS overrides
|
||||
├── img/
|
||||
│ ├── access_restricted_banner.png # Login page background image
|
||||
│ ├── favicon_256.png # Module editor logo (256×256)
|
||||
│ ├── favicon.gif / favicon.ico / favicon.svg # Favicon variants
|
||||
│ ├── logo.png / logo.svg # MokoCRM logos
|
||||
│ └── index.php # Directory index
|
||||
├── js/
|
||||
│ └── mokocrm.js.php # Dynamic JS (dev indicators, title suffix)
|
||||
├── langs/
|
||||
│ └── en_US/
|
||||
│ └── mokocrm.lang # English translations
|
||||
├── lib/
|
||||
│ └── mokocrm.lib.php # Admin page helper functions
|
||||
└── ChangeLog.md # Module changelog
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`src/core/modules/modMokoCRM.class.php`) is the core configuration file.
|
||||
|
||||
### Key Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modMokoCRM extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Official module ID (registered at wiki.dolibarr.org)
|
||||
$this->numero = 185067;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'mokocrm';
|
||||
$this->family = 'mokoconsulting';
|
||||
$this->module_position = 9999999999;
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "MokoCRM white labels Dolibarr ERP/CRM under the MokoCRM brand";
|
||||
|
||||
// Author / editor info
|
||||
$this->editor_name = 'Moko Consulting';
|
||||
$this->editor_url = 'https://mokoconsulting.tech';
|
||||
$this->editor_squarred_logo = 'favicon_256.png@mokocrm'; // shown on the module card
|
||||
|
||||
// Version — use 'development' to enable dev-mode indicators (see below)
|
||||
$this->version = '01.01.00';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("mokocrm@mokocrm");
|
||||
|
||||
// White label: override Dolibarr branding translations
|
||||
$this->overwrite_translation = array(
|
||||
'en_US:DolibarrProductName' => 'MokoCRM',
|
||||
'en_US:Dolibarr' => 'MokoCRM',
|
||||
);
|
||||
|
||||
// Enable CSS, JS and substitution white label features
|
||||
$this->module_parts = array(
|
||||
'substitutions' => 1,
|
||||
'css' => array('/mokocrm/css/mokocrm.css.php'),
|
||||
'js' => array('/mokocrm/js/mokocrm.js.php'),
|
||||
// ... other parts
|
||||
);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## White Labeling
|
||||
|
||||
MokoCRM applies three layers of white labeling:
|
||||
|
||||
### 1. Translation Overrides (`overwrite_translation`)
|
||||
|
||||
Set in `modMokoCRM.class.php`, this replaces standard Dolibarr translation strings with MokoCRM equivalents throughout the UI without modifying core files.
|
||||
|
||||
```php
|
||||
$this->overwrite_translation = array(
|
||||
'en_US:DolibarrProductName' => 'MokoCRM',
|
||||
'en_US:Dolibarr' => 'MokoCRM',
|
||||
);
|
||||
```
|
||||
|
||||
To add more overrides for other languages, add additional entries:
|
||||
|
||||
```php
|
||||
$this->overwrite_translation = array(
|
||||
'en_US:DolibarrProductName' => 'MokoCRM',
|
||||
'en_US:Dolibarr' => 'MokoCRM',
|
||||
'fr_FR:DolibarrProductName' => 'MokoCRM',
|
||||
'fr_FR:Dolibarr' => 'MokoCRM',
|
||||
);
|
||||
```
|
||||
|
||||
### 2. CSS Overrides (`css/mokocrm.css.php`)
|
||||
|
||||
Loaded on every page when the module is active. Use this to override visual branding elements.
|
||||
|
||||
### 3. Substitution Functions (`core/substitutions/functions_mokocrm.lib.php`)
|
||||
|
||||
Called when generating documents and emails. The function `getSubstitutionArray_mokocrm()` injects substitution variables that replace Dolibarr references in generated content.
|
||||
|
||||
### 4. JavaScript (`js/mokocrm.js.php`)
|
||||
|
||||
Served as `application/javascript` and loaded on every page when the module is active. Currently handles development environment indicators (see [Development Environment Indicators](#development-environment-indicators) below).
|
||||
|
||||
## Development Environment Indicators
|
||||
|
||||
When `$this->version` is set to `'development'` in `modMokoCRM.class.php`, the JS file (`js/mokocrm.js.php`) automatically activates two visible indicators on every page. No database write or install step is required — the gate is evaluated at PHP render time on each request.
|
||||
|
||||
### Title suffix
|
||||
|
||||
`document.title` is appended with `" - Development"` immediately and kept in sync via a `MutationObserver` so the suffix persists even after Dolibarr rewrites the title during AJAX navigation.
|
||||
|
||||
### Warning toast
|
||||
|
||||
An amber ⚠ warning toast is injected into `document.body` once per browser session (guarded by `sessionStorage`). It auto-dismisses after 10 seconds and includes a manual close button.
|
||||
|
||||
```
|
||||
⚠ Development Environment
|
||||
This is a non-production instance. Data entered here is for testing only
|
||||
and may be reset without notice. Do not enter real client or financial data.
|
||||
```
|
||||
|
||||
The toast is built entirely with `createElement` / `textContent` — no `innerHTML`, so it is CSP-safe.
|
||||
|
||||
### Enabling / disabling
|
||||
|
||||
| `$this->version` value | Dev indicators |
|
||||
|------------------------|---------------|
|
||||
| `'development'` | ✅ Active |
|
||||
| `'01.01.00'` (or any semver) | ❌ Off |
|
||||
|
||||
To switch a deployment into development mode, change the version string in `modMokoCRM.class.php`:
|
||||
|
||||
```php
|
||||
$this->version = 'development'; // enables indicators
|
||||
// $this->version = '01.01.00'; // production — no indicators
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "mokocrm_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->hasRight('mokocrm', 'read')) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use proper escaping
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "mokocrm_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "mokocrm_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "mokocrm_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in the language files:
|
||||
|
||||
```php
|
||||
// In langs/en_US/mokocrm.lang
|
||||
MokoCRMSetup = MokoCRM setup
|
||||
MokoCRMArea = Home MokoCRM
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("mokocrm@mokocrm");
|
||||
print $langs->trans("MokoCRMSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModMokoCRMTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class MokoCRMApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /mokocrm/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify white label branding appears correctly (check UI for "MokoCRM" instead of "Dolibarr")
|
||||
3. Check CSS overrides are loaded
|
||||
4. Verify substitutions work in generated documents
|
||||
5. Test with different user roles
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `<dolibarr_data>/dolibarr.log`
|
||||
|
||||
## Managing Constants
|
||||
|
||||
Dolibarr provides two helper functions in `core/lib/admin.lib.php` for writing and removing global constants at runtime. MokoCRM uses these directly in `init()` and `remove()` for `MAIN_LOGIN_BACKGROUND` rather than the passive `$this->const` declarative array, because it gives full control: the value is (re-)written every time the module is activated and cleanly deleted on deactivation.
|
||||
|
||||
### Writing a constant — `dolibarr_set_const()`
|
||||
|
||||
```php
|
||||
require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
|
||||
|
||||
dolibarr_set_const(
|
||||
$this->db, // DoliDB handle
|
||||
'MAIN_LOGIN_BACKGROUND', // constant name
|
||||
'access_restricted_banner.png', // value
|
||||
'chaine', // type (chaine | int | yesno | …)
|
||||
0, // visible in admin UI (0 = no)
|
||||
'Login background image set by MokoCRM', // note / description
|
||||
$conf->entity // entity scope
|
||||
);
|
||||
```
|
||||
|
||||
`dolibarr_set_const()` performs an INSERT if the constant doesn't exist yet, or an UPDATE if it does. It is the equivalent of what Dolibarr's own admin pages (e.g. `admin/ihm.php`) do when the administrator configures the login background.
|
||||
|
||||
### Removing a constant — `dolibarr_del_const()`
|
||||
|
||||
```php
|
||||
require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
|
||||
|
||||
dolibarr_del_const($this->db, 'MAIN_LOGIN_BACKGROUND', $conf->entity);
|
||||
```
|
||||
|
||||
Call this in `remove()` to restore the Dolibarr default (no login background) when the module is deactivated.
|
||||
|
||||
### When to prefer `dolibarr_set_const` over `$this->const`
|
||||
|
||||
| Approach | Best for |
|
||||
|----------|---------|
|
||||
| `$this->const` array | Simple module-specific constants that Dolibarr manages automatically (set on activate, deleted on deactivate if `deleteonunactive=1`) |
|
||||
| `dolibarr_set_const()` | Shared/core constants like `MAIN_LOGIN_BACKGROUND`; cases where you need the value to be re-written (not just inserted) on every re-activation; or when you need error handling |
|
||||
|
||||
MokoCRM uses the officially registered Dolibarr module ID **185067**. This ID must not be changed. See [Module ID](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `src/core/modules/modMokoCRM.class.php`
|
||||
- `docs/changelog.md`
|
||||
- `src/ChangeLog.md`
|
||||
|
||||
## Publishing / Releasing
|
||||
|
||||
Before a release:
|
||||
|
||||
1. ✅ Update version number in `modMokoCRM.class.php`
|
||||
2. ✅ Update `docs/changelog.md` and `src/ChangeLog.md`
|
||||
3. ✅ Test on the minimum supported Dolibarr version (19.0)
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Create a GitHub release tag
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- [MokoCRM GitHub Issues](https://github.com/mokoconsulting-tech/MokoCRM/issues) for MokoCRM-specific questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,145 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and enabling MokoCRM on your Dolibarr instance.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing MokoCRM, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 19.0 or higher
|
||||
- **PHP**: Version 7.1 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- gd or imagick
|
||||
- curl
|
||||
- json
|
||||
- xml
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr `custom/` directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone the MokoCRM repository as `mokocrm`:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/MokoCRM.git mokocrm
|
||||
```
|
||||
|
||||
> **Important:** The directory must be named `mokocrm` — this is the module's internal identifier used throughout Dolibarr.
|
||||
|
||||
The module source files live in the `src/` subdirectory of the repository. You can either work from there directly or copy the contents of `src/` into the `mokocrm/` directory, depending on your deployment approach.
|
||||
|
||||
### 2. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/mokocrm
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/mokocrm -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/mokocrm -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 3. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find **MokoCRM** in the module list (look under the *Moko Consulting* family)
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 4. Configure Module Settings (optional)
|
||||
|
||||
After activation:
|
||||
|
||||
1. Go to **Home → Setup → Modules/Applications**
|
||||
2. Click on **MokoCRM** to access its configuration page
|
||||
3. Configure any required settings
|
||||
4. Save changes
|
||||
|
||||
## White Label Activation
|
||||
|
||||
Once MokoCRM is enabled, the following white labeling takes effect automatically:
|
||||
|
||||
| Mechanism | File | Effect |
|
||||
|-----------|------|--------|
|
||||
| Translation override | `modMokoCRM.class.php` | Replaces "Dolibarr" / "DolibarrProductName" labels with "MokoCRM" in the UI |
|
||||
| CSS override | `css/mokocrm.css.php` | Applies MokoCRM branding styles |
|
||||
| Substitution functions | `core/substitutions/functions_mokocrm.lib.php` | Replaces Dolibarr references in generated documents and emails |
|
||||
| Login background | `MAIN_LOGIN_BACKGROUND` constant | Sets `access_restricted_banner.png` as the login page background (removed when module is deactivated) |
|
||||
| JS indicators | `js/mokocrm.js.php` | When `$this->version === 'development'`: appends `" - Development"` to the browser title and shows an amber warning toast once per session |
|
||||
|
||||
No additional configuration is required for white labeling to work.
|
||||
|
||||
> **Development mode:** To enable the development environment indicators, set `$this->version = 'development'` in `src/core/modules/modMokoCRM.class.php`. The indicators are evaluated dynamically on each page request — no reinstall is needed.
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Verify the clone directory is named exactly `mokocrm`
|
||||
- Clear Dolibarr's module cache: go to **Home → Setup → Modules/Applications** and use the "Refresh modules list" option, or delete `<dolibarr_data>/temp/` contents
|
||||
- Check file permissions
|
||||
- Verify PHP syntax: `php -l src/core/modules/modMokoCRM.class.php`
|
||||
|
||||
### White Label Not Taking Effect
|
||||
|
||||
- Confirm the module is **activated** (green toggle in Modules/Applications)
|
||||
- Check that Dolibarr version is 19.0 or higher (required for `overwrite_translation`)
|
||||
- Check Dolibarr logs: `<dolibarr_data>/dolibarr.log`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure the Apache/Nginx user has read access to all module files
|
||||
- Check `conf.php` file permissions in the Dolibarr root
|
||||
|
||||
### Database Errors
|
||||
|
||||
- Verify database credentials in Dolibarr's `conf/conf.php`
|
||||
- Ensure the database user has sufficient permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove MokoCRM:
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find MokoCRM and click **Deactivate**
|
||||
3. Optionally, remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/mokocrm
|
||||
```
|
||||
|
||||
> **Note:** Deactivating the module removes its constants and menus but does not delete any data tables created by the module.
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Review the [Development Guide](development.md) to extend or customise MokoCRM
|
||||
- Read the [Changelog](changelog.md) for version history
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Create an issue in the [MokoCRM repository](https://github.com/mokoconsulting-tech/MokoCRM/issues)
|
||||
- Check Dolibarr logs: `<dolibarr_data>/dolibarr.log`
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,65 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID
|
||||
|
||||
MokoCRM uses the officially registered Dolibarr module ID **185067**.
|
||||
|
||||
## Registered ID
|
||||
|
||||
| Property | Value |
|
||||
|----------|-------|
|
||||
| Module ID | **185067** |
|
||||
| Module name | `MokoCRM` |
|
||||
| Rights class | `mokocrm` |
|
||||
| Organisation | Moko Consulting |
|
||||
| Distribution | Public |
|
||||
| Registered at | [wiki.dolibarr.org/index.php/List_of_modules_id](https://wiki.dolibarr.org/index.php/List_of_modules_id) |
|
||||
|
||||
This ID is set in `src/core/modules/modMokoCRM.class.php`:
|
||||
|
||||
```php
|
||||
$this->numero = 185067; // Official module ID registered at wiki.dolibarr.org
|
||||
```
|
||||
|
||||
## Why Module IDs Matter
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier. This ID is critical for:
|
||||
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations in the database (`llx_const`)
|
||||
- Permission ID generation (e.g., `18506701`, `18506702`, …)
|
||||
|
||||
## Dolibarr Module ID Ranges
|
||||
|
||||
| Range | Purpose |
|
||||
|-------|---------|
|
||||
| 0 – 94,999 | Core Dolibarr modules (reserved) |
|
||||
| 95,000 – 99,999 | Community modules (official Dolibarr repos) |
|
||||
| 100,000 – 499,999 | Third-party public modules |
|
||||
| 500,000 – 599,999 | Private / unlisted modules |
|
||||
| 600,000+ | Development / temporary (not for distribution) |
|
||||
|
||||
MokoCRM's ID **185067** falls in the **100,000 – 499,999** range, appropriate for a publicly distributed third-party module.
|
||||
|
||||
## Checking for Conflicts
|
||||
|
||||
To verify there is no ID conflict on a running Dolibarr installation, run:
|
||||
|
||||
```sql
|
||||
SELECT name, value FROM llx_const WHERE name = 'MAIN_MODULE_MOKOCRM';
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,103 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoCRM Roadmap
|
||||
|
||||
This document describes the planned development trajectory for MokoCRM. Completed milestones are included for historical context. Items within a future version are subject to change — open an issue to propose additions or reprioritisations.
|
||||
|
||||
## Status legend
|
||||
|
||||
| Symbol | Meaning |
|
||||
|---|---|
|
||||
| ✅ | Complete and released |
|
||||
| 🔄 | In progress (active development branch) |
|
||||
| 🗓️ | Planned (not yet started) |
|
||||
| 💡 | Under consideration |
|
||||
|
||||
---
|
||||
|
||||
## ✅ 01.00.00 — Foundation *(released 2026-03-10)*
|
||||
|
||||
Initial MokoCRM module release establishing the white-label base.
|
||||
|
||||
- ✅ Module descriptor (`modMokoCRM.class.php`) with official module ID **185067**
|
||||
- ✅ White-label translation overrides (`DolibarrProductName` → MokoCRM, `Dolibarr` → MokoCRM)
|
||||
- ✅ English translation file (`langs/en_US/mokocrm.lang`)
|
||||
- ✅ Admin setup page (`admin/setup.php`) and about page (`admin/about.php`)
|
||||
- ✅ Library file (`lib/mokocrm.lib.php`) with admin navigation helper
|
||||
- ✅ Comprehensive documentation (installation, development, module ID, changelog)
|
||||
|
||||
---
|
||||
|
||||
## ✅ 01.01.00 — Branding Polish *(released 2026-03-12)*
|
||||
|
||||
Login-page customisation and developer-mode indicators.
|
||||
|
||||
- ✅ Custom login page background (`access_restricted_banner.png`) set on activation, removed on deactivation
|
||||
- ✅ Module card editor logo (`favicon_256.png@mokocrm`) displayed in the Dolibarr admin panel
|
||||
- ✅ Development mode: one-time session toast warning when `$this->version === 'development'`
|
||||
- ✅ Development mode: `" — Development"` suffix appended to the browser tab title
|
||||
|
||||
---
|
||||
|
||||
## 🔄 01.02.00 — Documentation *(in progress — branch `dev/01.02.00`)*
|
||||
|
||||
Documentation overhaul.
|
||||
|
||||
- ✅ Regenerate all README files with accurate MokoCRM content (replacing moko-platform template placeholders)
|
||||
- ✅ Fix stale documentation and Makefile module identity (correct `MODULE_NAME`, `MODULE_VERSION`, `MODULE_NUMBER`, `SRC_DIR`)
|
||||
- ✅ Remove deleted deployment references from docs and changelog
|
||||
- ✅ Roadmap document (`docs/roadmap.md`)
|
||||
|
||||
---
|
||||
|
||||
## 🗓️ 01.03.00 — Extended White Label *(planned)*
|
||||
|
||||
Deeper brand coverage across more Dolibarr surfaces.
|
||||
|
||||
- 🗓️ French translation file (`langs/fr_FR/mokocrm.lang`) mirroring the English keys
|
||||
- 🗓️ Custom help URL override — replace Dolibarr help links with MokoCRM documentation
|
||||
- 🗓️ CSS overrides for the Dolibarr top-bar logo and favicon injection
|
||||
- 🗓️ Custom "About" content driven by module constants rather than hardcoded strings
|
||||
|
||||
---
|
||||
|
||||
## 🗓️ 01.04.00 — Admin Experience *(planned)*
|
||||
|
||||
Quality-of-life improvements for administrators managing a MokoCRM instance.
|
||||
|
||||
- 🗓️ Admin dashboard widget showing module version, active features, and support links
|
||||
- 🗓️ Setup page: configurable company name and support URL constants stored in `llx_const`
|
||||
- 🗓️ Setup page: one-click "apply branding" action to refresh all white-label constants
|
||||
|
||||
---
|
||||
|
||||
## 💡 Under consideration
|
||||
|
||||
These items have no committed version yet. Open an issue to discuss prioritisation.
|
||||
|
||||
- 💡 Multi-entity support — per-entity white-label overrides for hosted/multi-tenant deployments
|
||||
- 💡 Theme selection — allow administrators to switch between bundled CSS colour themes
|
||||
- 💡 Custom email footer — inject MokoCRM branding into outbound Dolibarr emails
|
||||
- 💡 Automated compatibility matrix — CI job to test against multiple Dolibarr versions
|
||||
|
||||
---
|
||||
|
||||
## Contributing
|
||||
|
||||
To propose a new roadmap item:
|
||||
|
||||
1. Open an issue at [mokoconsulting-tech/MokoCRM/issues](https://github.com/mokoconsulting-tech/MokoCRM/issues) describing the feature and its value
|
||||
2. Reference the issue in a pull request targeting the relevant `dev/X.Y.Z` branch
|
||||
3. Follow the contribution guidelines in [CONTRIBUTING.md](CONTRIBUTING)
|
||||
|
||||
---
|
||||
|
||||
*Last updated: 2026-03-19*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,112 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module Update Server
|
||||
|
||||
This module uses `update.json` hosted in the repo root to enable Dolibarr's built-in update checker.
|
||||
|
||||
## How It Works
|
||||
|
||||
1. When a PR is merged to `main`, the `auto-release.yml` workflow:
|
||||
- Reads the version from `README.md`
|
||||
- Sets `$this->version` in the module descriptor to the real version
|
||||
- Creates a GitHub Release with a git tag
|
||||
- Writes `update.json` to the repo root
|
||||
2. The module descriptor's `$this->url_last_version` points to the raw `update.json` URL
|
||||
3. Dolibarr's admin panel fetches this URL to check for available updates
|
||||
|
||||
## Setup
|
||||
|
||||
### 1. Module Descriptor
|
||||
|
||||
In `src/core/modules/mod*.class.php`, ensure these lines are in the constructor:
|
||||
|
||||
```php
|
||||
// Version — 'development' on dev branches, real version set by auto-release on merge to main
|
||||
$this->version = 'development';
|
||||
|
||||
// Update check — points to update.json written by auto-release workflow
|
||||
$this->url_last_version = 'https://raw.githubusercontent.com/mokoconsulting-tech/REPO_NAME/main/update.json';
|
||||
```
|
||||
|
||||
Replace `REPO_NAME` with this repository's name.
|
||||
|
||||
### 2. Version Parser
|
||||
|
||||
Add this method to the module descriptor class to parse the JSON response:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get the latest available version from the update server.
|
||||
*
|
||||
* Reads update.json from the GitHub repo and extracts the version field.
|
||||
* Called by Dolibarr's module update checker.
|
||||
*
|
||||
* @return string Latest version number, or empty string on failure
|
||||
*/
|
||||
public function getLatestVersion(): string
|
||||
{
|
||||
if (empty($this->url_last_version)) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$content = @file_get_contents($this->url_last_version);
|
||||
if ($content === false) {
|
||||
return '';
|
||||
}
|
||||
|
||||
$data = json_decode($content, true);
|
||||
return $data['version'] ?? '';
|
||||
}
|
||||
```
|
||||
|
||||
### 3. That's It
|
||||
|
||||
Everything else is automated:
|
||||
- `deploy-dev.yml` sets version to `"development"` on dev branches
|
||||
- `auto-release.yml` sets the real version and writes `update.json` on release
|
||||
- `sync-version-on-merge.yml` bumps the patch version in README.md
|
||||
|
||||
## update.json Format
|
||||
|
||||
```json
|
||||
{
|
||||
"version": "01.02.03",
|
||||
"tag": "v01.02.03",
|
||||
"repo": "mokoconsulting-tech/REPO_NAME",
|
||||
"release_url": "https://github.com/mokoconsulting-tech/REPO_NAME/releases/tag/v01.02.03",
|
||||
"updated": "2026-03-27T00:00:00Z"
|
||||
}
|
||||
```
|
||||
|
||||
> **Do not edit `update.json` manually** — it is auto-generated by the release workflow.
|
||||
|
||||
## Version Lifecycle
|
||||
|
||||
```
|
||||
dev/** branch → $this->version = "development" (no update.json)
|
||||
merge to main → $this->version = "01.02.03" → update.json written → GitHub Release
|
||||
next commit → README auto-bumps to 01.02.04 (no release yet)
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
| Issue | Solution |
|
||||
|-------|----------|
|
||||
| `update.json` doesn't exist | Merge a PR to main — the first release creates it |
|
||||
| Version shows "development" | Expected on `dev/**` branches — real version set on release |
|
||||
| Dolibarr doesn't detect updates | Check `$this->url_last_version` URL returns valid JSON |
|
||||
| Wrong version in update.json | Check README.md VERSION field — it's the source of truth |
|
||||
|
||||
### Test the URL
|
||||
|
||||
```bash
|
||||
curl -s https://raw.githubusercontent.com/mokoconsulting-tech/REPO_NAME/main/update.json | jq .
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoCRM](https://git.mokoconsulting.tech/MokoConsulting/MokoCRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,28 @@
|
||||
# MokoDPCalendarAPI
|
||||
|
||||
Joomla Web Services plugin exposing DPCalendar events, calendars, and locations via REST API
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDPCalendarAPI) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [INSTALLATION](INSTALLATION) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDPCalendarAPI](https://git.mokoconsulting.tech/MokoConsulting/MokoDPCalendarAPI) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,51 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- Joomla 5.x or 6.x
|
||||
- DPCalendar 9.x+ installed and enabled
|
||||
- PHP 8.1+
|
||||
|
||||
## Install from Release
|
||||
|
||||
1. Download the latest ZIP from Releases
|
||||
2. In Joomla admin: **System > Install > Extensions**
|
||||
3. Upload and install the ZIP
|
||||
4. Go to **System > Manage > Plugins**
|
||||
5. Search for "DPCalendar" and enable **Web Services - DPCalendar**
|
||||
|
||||
## Install from Source
|
||||
|
||||
```sh
|
||||
git clone https://git.mokoconsulting.tech/MokoConsulting/MokoDPCalendarAPI.git
|
||||
cd MokoDPCalendarAPI
|
||||
```
|
||||
|
||||
Install the `src/` directory as a Joomla extension via Install from Folder or symlink.
|
||||
|
||||
## Verify
|
||||
|
||||
```sh
|
||||
curl -s https://your-site.com/api/index.php/v1/dpcalendar/events \
|
||||
-H "Authorization: Bearer YOUR_API_TOKEN" \
|
||||
-H "Accept: application/vnd.api+json"
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### "Resource not found"
|
||||
- Ensure the plugin is enabled in Plugins manager
|
||||
- Verify DPCalendar component is installed
|
||||
|
||||
### Empty responses
|
||||
- Check API user has access to the calendars
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDPCalendarAPI](https://git.mokoconsulting.tech/MokoConsulting/MokoDPCalendarAPI) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,46 @@
|
||||
# MokoDoliAdInsights
|
||||
|
||||
A Dolibarr module used to bridge multiple advertising services (Google Ads, Meta Ads, LinkedIn Ads, etc.) reporting with Claude AI analysis
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
| [quickstart service](quickstart-service.-.-) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
| [architecture](architecture) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [adding services](adding-services.-.-) | ← [Home](Home) |
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,243 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliAdInsights Documentation
|
||||
|
||||
Welcome to the **MokoDoliAdInsights** module documentation. This module integrates multiple advertising platforms (Google Ads, Facebook Ads, Microsoft Ads, and more) with Claude AI analysis in your Dolibarr ERP/CRM system.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Get started with installing the module
|
||||
- [Architecture Overview](architecture.md) - Understand the multi-platform design
|
||||
- [Development Guide](development.md) - Learn how to extend the module
|
||||
- [Adding Services](adding-services.md) - Add support for new ad platforms (plugin system)
|
||||
- [Changelog](changelog.md) - Track version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For New Users
|
||||
|
||||
If you're new to this module, start here:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Platform-specific API credential setup
|
||||
- Configuration and testing
|
||||
- Troubleshooting common issues
|
||||
|
||||
2. **Module Overview**
|
||||
- **Multi-Platform Support**: Connect to Google Ads, Facebook Ads, or Microsoft Ads
|
||||
- **Claude AI Integration**: Get AI-powered insights and recommendations
|
||||
- **Campaign Reports**: Generate comprehensive performance reports
|
||||
- **Extensible Architecture**: Easy to add support for additional platforms
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're extending the module or adding new ad platforms:
|
||||
|
||||
1. **[Architecture Overview](architecture.md)**
|
||||
- Interface-based design pattern
|
||||
- Services architecture (new!)
|
||||
- Factory pattern implementation
|
||||
- Data flow and structure
|
||||
- Database schema
|
||||
|
||||
2. **[Development Guide](development.md)**
|
||||
- Module structure and organization
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
3. **[Adding Services](adding-services.md)** - **NEW!**
|
||||
- Complete guide to adding new ad platforms
|
||||
- Service architecture explained
|
||||
- Step-by-step implementation
|
||||
- Code examples and templates
|
||||
- Best practices for services
|
||||
- OAuth, rate limiting, error handling
|
||||
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
- **[src/README.md](src-README)** - Detailed module documentation
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Which ad platforms are supported?**
|
||||
A: Currently Google Ads, Facebook Ads, and Microsoft Ads. The architecture makes it easy to add more platforms.
|
||||
|
||||
**Q: How do I switch between ad platforms?**
|
||||
A: Go to module configuration and select your preferred ad system from the dropdown.
|
||||
|
||||
**Q: Can I use multiple ad platforms simultaneously?**
|
||||
A: Currently, one platform is active at a time. You can switch between them in configuration.
|
||||
|
||||
**Q: How do I add a new ad platform?**
|
||||
A: See the [Adding Services guide](adding-services.md) for step-by-step instructions.
|
||||
|
||||
**Q: Where do I get API credentials?**
|
||||
A: Each platform has its own developer console:
|
||||
- **Google Ads**: https://ads.google.com/home/tools/manager-accounts/
|
||||
- **Facebook Ads**: https://developers.facebook.com/apps/
|
||||
- **Microsoft Ads**: https://ads.microsoft.com/
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Claude AI Docs**: https://docs.anthropic.com/
|
||||
|
||||
## Key Concepts
|
||||
|
||||
### Ad System Clients
|
||||
|
||||
All ad platform integrations implement the `AdSystemClientInterface`:
|
||||
|
||||
```php
|
||||
interface AdSystemClientInterface {
|
||||
public function getSystemName(); // e.g., 'googleads'
|
||||
public function getSystemDisplayName(); // e.g., 'Google Ads'
|
||||
public function isConfigured();
|
||||
public function fetchCampaignData($dateStart, $dateEnd);
|
||||
public function getError();
|
||||
}
|
||||
```
|
||||
|
||||
### Factory Pattern
|
||||
|
||||
The `AdSystemFactory` creates the appropriate client based on configuration:
|
||||
|
||||
```php
|
||||
// Get client for configured system
|
||||
$client = AdSystemFactory::create($db);
|
||||
|
||||
// Or specify a system
|
||||
$client = AdSystemFactory::create($db, 'googleads');
|
||||
```
|
||||
|
||||
### Unified Data Format
|
||||
|
||||
All platforms return data in a standardized format:
|
||||
|
||||
```json
|
||||
{
|
||||
"ad_system": "googleads|facebookads|microsoftads",
|
||||
"ad_system_display": "Google Ads|Facebook Ads|Microsoft Ads",
|
||||
"campaigns": [...],
|
||||
"totals": {...},
|
||||
"period": {...}
|
||||
}
|
||||
```
|
||||
|
||||
## Module Architecture
|
||||
|
||||
**New Services Architecture (v1.3.0+):**
|
||||
```
|
||||
services/
|
||||
├── AdServiceInterface (interface)
|
||||
├── BaseAdService (abstract class)
|
||||
├── google/GoogleAdsService
|
||||
├── facebook/FacebookAdsService
|
||||
├── microsoft/MicrosoftAdsService
|
||||
└── examples/ExampleAdService (template)
|
||||
|
||||
AdServiceFactory
|
||||
└── create($db, $serviceId) → returns service
|
||||
|
||||
Report (data model)
|
||||
├── ad_system_data (campaign data JSON)
|
||||
├── ad_system_type (platform identifier)
|
||||
└── report_type (program/competitive/general)
|
||||
```
|
||||
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Create ad system client
|
||||
$client = AdSystemFactory::create($db, 'googleads');
|
||||
|
||||
// Check if configured
|
||||
if ($client->isConfigured()) {
|
||||
$data = $client->fetchCampaignData($dateStart, $dateEnd);
|
||||
}
|
||||
```
|
||||
|
||||
```bash
|
||||
# Install module in Dolibarr
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliAdInsights.git mokodoliadinsights
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file in the `docs/` directory
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Module Name**: MokoDoliAdInsights (starts with MokoDoli, references Dolibarr)
|
||||
- **Module Version**: 1.3.0 (in development)
|
||||
- **Last Updated**: 2026-03-04
|
||||
- **Minimum Dolibarr Version**: 19.0
|
||||
- **PHP Version**: 7.4+
|
||||
- **Supported Ad Platforms**:
|
||||
- Google Ads API
|
||||
- Facebook Marketing API
|
||||
- Microsoft Advertising API
|
||||
- **Extensible**: Easy to add more platforms via services architecture
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Documentation
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Google Ads API](https://developers.google.com/google-ads/api/docs/start)
|
||||
- [Facebook Marketing API](https://developers.facebook.com/docs/marketing-apis)
|
||||
- [Microsoft Advertising API](https://docs.microsoft.com/en-us/advertising/guides/)
|
||||
- [Claude AI API](https://docs.anthropic.com/)
|
||||
|
||||
### MokoConsulting Tech
|
||||
|
||||
- [GitHub Organization](https://github.com/mokoconsulting-tech)
|
||||
- [MokoDoliAdInsights Repository](https://github.com/mokoconsulting-tech/MokoDoliAdInsights)
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- New to the module? Start with [Installation Guide](installation.md)
|
||||
- Want to understand the architecture? Check [Architecture Overview](architecture.md)
|
||||
- Ready to develop? Read the [Development Guide](development.md)
|
||||
- Adding a new platform? See [Adding Services](adding-services.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,309 @@
|
||||
← [Home](Home)
|
||||
|
||||
# How to Add a New Ad Platform Service
|
||||
|
||||
This guide walks you through adding support for a new advertising platform to
|
||||
**MokoDoliAdInsights**.
|
||||
|
||||
## Overview
|
||||
|
||||
MokoDoliAdInsights uses a service-based plugin architecture. Adding a new
|
||||
platform requires **no changes to the factory or the admin setup page** —
|
||||
`AdSystemFactory` discovers services automatically by scanning the
|
||||
`src/services/` directory at runtime.
|
||||
|
||||
## What You Need To Do
|
||||
|
||||
1. Create the service class file (and directory)
|
||||
2. Add translations (display name + config field labels)
|
||||
3. *(Optional)* Create a `README.md` for your service
|
||||
|
||||
That's it. The factory, the admin dropdown, and the configuration form sections
|
||||
are all populated automatically.
|
||||
|
||||
---
|
||||
|
||||
## Step 1 — Create the Service Directory and Class
|
||||
|
||||
```bash
|
||||
cd src/services/
|
||||
mkdir yourplatform
|
||||
```
|
||||
|
||||
Create `src/services/yourplatform/YourPlatformService.class.php`:
|
||||
|
||||
```php
|
||||
<?php
|
||||
require_once __DIR__.'/../BaseAdService.class.php';
|
||||
|
||||
class YourPlatformService extends BaseAdService
|
||||
{
|
||||
/**
|
||||
* SERVICE_ID — unique lowercase identifier, no spaces.
|
||||
* SERVICE_NAME — human-readable display name shown in dropdowns.
|
||||
*
|
||||
* These two constants trigger auto-discovery. No other file needs editing.
|
||||
*/
|
||||
const SERVICE_ID = 'yourplatform';
|
||||
const SERVICE_NAME = 'Your Platform Name';
|
||||
|
||||
public function __construct(DoliDB $db)
|
||||
{
|
||||
$this->serviceId = self::SERVICE_ID;
|
||||
$this->serviceName = self::SERVICE_NAME;
|
||||
$this->provider = 'your_company';
|
||||
parent::__construct($db);
|
||||
}
|
||||
|
||||
// --- Required method implementations below ---
|
||||
|
||||
protected function loadConfiguration()
|
||||
{
|
||||
$this->config = array(
|
||||
'api_key' => getDolGlobalString('MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY'),
|
||||
'account_id' => getDolGlobalString('MOKODOLIADINSIGHTS_YOURPLATFORM_ACCOUNT_ID'),
|
||||
);
|
||||
}
|
||||
|
||||
public function isConfigured()
|
||||
{
|
||||
return $this->isConfigValueSet('api_key') &&
|
||||
$this->isConfigValueSet('account_id');
|
||||
}
|
||||
|
||||
public function validateCredentials()
|
||||
{
|
||||
if (!$this->isConfigured()) {
|
||||
$this->setError('Service not configured');
|
||||
return false;
|
||||
}
|
||||
// Make a lightweight test API call here
|
||||
return true;
|
||||
}
|
||||
|
||||
public function fetchCampaignData($dateStart, $dateEnd, $options = array())
|
||||
{
|
||||
if (!$this->isConfigured()) {
|
||||
$this->setError('Service not configured');
|
||||
return false;
|
||||
}
|
||||
try {
|
||||
$start = $this->normalizeDate($dateStart);
|
||||
$end = $this->normalizeDate($dateEnd);
|
||||
|
||||
// TODO: call your platform's API and build $campaigns / $totals arrays
|
||||
$campaigns = array();
|
||||
$totals = array('impressions' => 0, 'clicks' => 0, 'spend' => 0.0);
|
||||
|
||||
return $this->formatResponse($campaigns, $totals, $dateStart, $dateEnd);
|
||||
} catch (Exception $e) {
|
||||
$this->setError('Failed to fetch data: ' . $e->getMessage());
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public function getAvailableMetrics()
|
||||
{
|
||||
return array(
|
||||
'impressions' => array('name' => 'Impressions', 'type' => 'integer'),
|
||||
'clicks' => array('name' => 'Clicks', 'type' => 'integer'),
|
||||
'spend' => array('name' => 'Spend', 'type' => 'currency', 'currency' => 'USD'),
|
||||
'ctr' => array('name' => 'CTR', 'type' => 'percentage', 'calculated' => true),
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Defines the credential fields shown in the admin configuration form.
|
||||
* These are rendered automatically by admin/setup.php — no edits needed there.
|
||||
*
|
||||
* 'secure' => true causes the value to be encrypted in the database.
|
||||
* 'placeholder' shown in the input field as a hint.
|
||||
* 'description' shown as help text next to the field.
|
||||
*/
|
||||
public function getConfigurationFields()
|
||||
{
|
||||
return array(
|
||||
'MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY' => array(
|
||||
'label' => 'API Key',
|
||||
'type' => 'text',
|
||||
'required' => true,
|
||||
'secure' => true,
|
||||
'description' => 'Your Platform API key',
|
||||
),
|
||||
'MOKODOLIADINSIGHTS_YOURPLATFORM_ACCOUNT_ID' => array(
|
||||
'label' => 'Account ID',
|
||||
'type' => 'text',
|
||||
'required' => true,
|
||||
'secure' => false,
|
||||
'description' => 'Your advertising account ID',
|
||||
'placeholder' => 'acct_123456789',
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
public function getCapabilities()
|
||||
{
|
||||
return array(
|
||||
'campaign_reporting',
|
||||
'date_range_filtering',
|
||||
);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Auto-Discovery Rules
|
||||
|
||||
`AdSystemFactory` discovers your service if **all** of the following are true:
|
||||
|
||||
| Rule | Detail |
|
||||
|------|--------|
|
||||
| Subdirectory of `src/services/` | Direct child directory only |
|
||||
| Not `examples/` | That directory is reserved for templates |
|
||||
| Filename `<ClassName>Service.class.php` | Class name must match filename |
|
||||
| Class extends `BaseAdService` | Via `is_subclass_of()` check |
|
||||
| `const SERVICE_ID` is a non-empty string | Acts as the registry key |
|
||||
|
||||
---
|
||||
|
||||
## Step 2 — Add Translations
|
||||
|
||||
Edit `src/langs/en_US/mokodoliadinsights.lang` and add:
|
||||
|
||||
```
|
||||
# Your Platform
|
||||
YourPlatformName = Your Platform Name
|
||||
YourPlatformNameSection = Your Platform Name Configuration
|
||||
MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY = API Key
|
||||
MOKODOLIADINSIGHTS_YOURPLATFORM_ACCOUNT_ID = Account ID
|
||||
```
|
||||
|
||||
**Naming convention for the section heading key:**
|
||||
Remove all spaces from `SERVICE_NAME` and append `Section`:
|
||||
`'Your Platform Name'` → `'YourPlatformNameSection'`
|
||||
|
||||
If no translation key is found Dolibarr falls back to displaying the raw key,
|
||||
so adding translations is recommended but not strictly required.
|
||||
|
||||
---
|
||||
|
||||
## Step 3 — *(Optional)* Create a README
|
||||
|
||||
Document platform-specific setup in
|
||||
`src/services/yourplatform/README.md`:
|
||||
|
||||
```markdown
|
||||
# Your Platform Service
|
||||
|
||||
## Requirements
|
||||
- Your Platform account with API access
|
||||
|
||||
## Getting Credentials
|
||||
1. Log in to the developer dashboard
|
||||
2. Create an API key under Settings → API Access
|
||||
|
||||
## Supported Features
|
||||
- Campaign reporting
|
||||
- Date range filtering
|
||||
|
||||
## Known Limitations
|
||||
- Maximum 90-day date range
|
||||
- Rate limit: 100 req/hour
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Verifying the Integration
|
||||
|
||||
After adding your service:
|
||||
|
||||
1. Open the MokoDoliAdInsights admin setup page.
|
||||
2. Confirm **Your Platform Name** appears in the **Ad System** dropdown.
|
||||
3. Confirm the **Your Platform Name Configuration** section appears with the
|
||||
fields defined in `getConfigurationFields()`.
|
||||
4. Enter credentials and save.
|
||||
5. Navigate to **Generate Report**, select the new platform, and verify data is
|
||||
fetched.
|
||||
|
||||
---
|
||||
|
||||
## Reference
|
||||
|
||||
### Files You Always Edit
|
||||
|
||||
| File | What to add |
|
||||
|------|-------------|
|
||||
| `src/services/<platform>/<Name>Service.class.php` | The service class (required) |
|
||||
| `src/langs/en_US/mokodoliadinsights.lang` | Translation strings (recommended) |
|
||||
|
||||
### Files You Never Need to Edit
|
||||
|
||||
| File | Why it's automatic |
|
||||
|------|-------------------|
|
||||
| `src/class/adsystemfactory.class.php` | Auto-discovers from `src/services/` |
|
||||
| `src/admin/setup.php` | Generates config sections from `getConfigurationFields()` |
|
||||
|
||||
### BaseAdService Helper Methods
|
||||
|
||||
```php
|
||||
// Configuration
|
||||
protected function isConfigValueSet($key); // true/false
|
||||
protected function getConfigValue($key, $default); // read config value
|
||||
protected function loadConfiguration(); // override to load credentials
|
||||
|
||||
// Data
|
||||
protected function normalizeDate($date); // date/timestamp → int
|
||||
protected function formatResponse($campaigns, $totals, $start, $end); // standard JSON
|
||||
|
||||
// Error handling
|
||||
protected function setError($message); // store error
|
||||
public function getError(); // retrieve last error
|
||||
```
|
||||
|
||||
### Standard Response Format
|
||||
|
||||
`formatResponse()` produces:
|
||||
|
||||
```json
|
||||
{
|
||||
"service_id": "yourplatform",
|
||||
"service_name": "Your Platform Name",
|
||||
"provider": "your_company",
|
||||
"campaigns": [ { "id": "...", "name": "...", "impressions": 0 } ],
|
||||
"totals": { "impressions": 0, "clicks": 0, "spend": 0.0 },
|
||||
"period": { "start": "2025-01-01", "end": "2025-01-31" },
|
||||
"generated_at": "2025-01-31 12:00:00"
|
||||
}
|
||||
```
|
||||
|
||||
### Capabilities You Can Declare
|
||||
|
||||
```php
|
||||
public function getCapabilities()
|
||||
{
|
||||
return array(
|
||||
'campaign_reporting', // basic campaign metrics
|
||||
'conversion_tracking', // conversion data
|
||||
'date_range_filtering', // custom date ranges
|
||||
'geographic_breakdown', // geographic data
|
||||
'device_breakdown', // device-specific data
|
||||
'video_metrics', // video views / completion
|
||||
'video_completion_tracking',// quartile completion rates
|
||||
'engagement_tracking', // likes, shares, comments
|
||||
'audience_insights', // audience demographics
|
||||
'keyword_analysis', // keyword performance
|
||||
);
|
||||
}
|
||||
```
|
||||
|
||||
### Example Service
|
||||
|
||||
See `src/services/examples/ExampleAdService.class.php` for a complete
|
||||
annotated template.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,634 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Architecture Overview
|
||||
|
||||
This document explains the technical architecture of the MokoDoliAdInsights module and how it achieves multi-platform advertising system integration with Claude AI analysis.
|
||||
|
||||
## Design Principles
|
||||
|
||||
The module is built on these core principles:
|
||||
|
||||
1. **Interface-based Design**: All ad clients implement a common interface
|
||||
2. **Factory Pattern**: Centralized client instantiation
|
||||
3. **Extensibility**: Easy to add new platforms
|
||||
4. **Security**: Encrypted credential storage
|
||||
5. **Separation of Concerns**: Clear boundaries between data fetching, analysis, and presentation
|
||||
|
||||
## System Architecture
|
||||
|
||||
```
|
||||
┌─────────────────────────────────────────────────────────────┐
|
||||
│ Dolibarr Interface │
|
||||
│ (Admin UI, Report Pages, Dashboard, Scheduled Tasks) │
|
||||
└───────────────────────┬─────────────────────────────────────┘
|
||||
│
|
||||
┌───────────────────────▼─────────────────────────────────────┐
|
||||
│ AdSystemFactory │
|
||||
│ • create($db, $system) │
|
||||
│ • getAvailableSystems() │
|
||||
│ • getCurrentSystem() │
|
||||
└───────────────────────┬─────────────────────────────────────┘
|
||||
│
|
||||
┌──────────────┼──────────────┐
|
||||
│ │ │
|
||||
┌────────▼───────┐ ┌───▼───────┐ ┌───▼──────────┐
|
||||
│ GoogleAdsClient│ │FacebookAds│ │MicrosoftAds │
|
||||
│ │ │ Client │ │ Client │
|
||||
└────────┬───────┘ └───┬───────┘ └───┬──────────┘
|
||||
│ │ │
|
||||
└─────────────┼─────────────┘
|
||||
│ implements
|
||||
┌─────────────▼──────────────┐
|
||||
│ AdSystemClientInterface │
|
||||
│ • getSystemName() │
|
||||
│ • getSystemDisplayName() │
|
||||
│ • isConfigured() │
|
||||
│ • fetchCampaignData() │
|
||||
│ • getError() │
|
||||
└─────────────┬───────────────┘
|
||||
│
|
||||
┌─────────────▼───────────────┐
|
||||
│ Report Class │
|
||||
│ • ad_system_data │
|
||||
│ • ad_system_type │
|
||||
│ • claude_analysis │
|
||||
└─────────────┬───────────────┘
|
||||
│
|
||||
┌─────────────▼───────────────┐
|
||||
│ Claude AI Client │
|
||||
│ • analyzeData() │
|
||||
│ • generateInsights() │
|
||||
└──────────────────────────────┘
|
||||
```
|
||||
|
||||
## Core Components
|
||||
|
||||
### 1. AdSystemClientInterface
|
||||
|
||||
The foundation of the multi-platform architecture. All ad system clients must implement this interface.
|
||||
|
||||
|
||||
**Methods**:
|
||||
|
||||
```php
|
||||
interface AdSystemClientInterface
|
||||
{
|
||||
/**
|
||||
* Get the system identifier (e.g., 'googleads', 'facebookads')
|
||||
* @return string
|
||||
*/
|
||||
public function getSystemName();
|
||||
|
||||
/**
|
||||
* Get the display name (e.g., 'Google Ads', 'Facebook Ads')
|
||||
* @return string
|
||||
*/
|
||||
public function getSystemDisplayName();
|
||||
|
||||
/**
|
||||
* Check if all required credentials are configured
|
||||
* @return bool
|
||||
*/
|
||||
public function isConfigured();
|
||||
|
||||
/**
|
||||
* Fetch campaign data for the specified date range
|
||||
* @param string|int $dateStart
|
||||
* @param string|int $dateEnd
|
||||
* @return string|false JSON-encoded data or false on error
|
||||
*/
|
||||
public function fetchCampaignData($dateStart, $dateEnd);
|
||||
|
||||
/**
|
||||
* Get the last error message
|
||||
* @return string
|
||||
*/
|
||||
public function getError();
|
||||
}
|
||||
```
|
||||
|
||||
**Purpose**:
|
||||
- Ensures consistency across all ad platform implementations
|
||||
- Makes the codebase predictable and maintainable
|
||||
- Allows polymorphic usage of clients
|
||||
|
||||
### 2. Ad System Clients
|
||||
|
||||
Individual implementations for each advertising platform.
|
||||
|
||||
#### GoogleAdsClient
|
||||
|
||||
|
||||
**Configuration Requirements**:
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CLIENT_ID`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CLIENT_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_DEVELOPER_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_REFRESH_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CUSTOMER_ID`
|
||||
|
||||
**Data Structure**:
|
||||
```json
|
||||
{
|
||||
"ad_system": "googleads",
|
||||
"ad_system_display": "Google Ads",
|
||||
"campaigns": [
|
||||
{
|
||||
"id": "12345678",
|
||||
"name": "Campaign Name",
|
||||
"impressions": 10000,
|
||||
"clicks": 250,
|
||||
"cost": 125.50,
|
||||
"conversions": 15,
|
||||
"ctr": 2.50,
|
||||
"cpc": 0.50
|
||||
}
|
||||
],
|
||||
"totals": {...},
|
||||
"period": {...}
|
||||
}
|
||||
```
|
||||
|
||||
#### FacebookAdsClient
|
||||
|
||||
|
||||
**Configuration Requirements**:
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_APP_ID`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_APP_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_ACCESS_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_ACCOUNT_ID`
|
||||
|
||||
#### MicrosoftAdsClient
|
||||
|
||||
|
||||
**Configuration Requirements**:
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_CLIENT_ID`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_CLIENT_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_DEVELOPER_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_REFRESH_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_ACCOUNT_ID`
|
||||
|
||||
### 3. AdSystemFactory
|
||||
|
||||
Centralized factory for creating ad system clients.
|
||||
|
||||
|
||||
**Methods**:
|
||||
|
||||
```php
|
||||
class AdSystemFactory
|
||||
{
|
||||
/**
|
||||
* Get list of available ad systems
|
||||
* @return array ['googleads' => 'Google Ads', ...]
|
||||
*/
|
||||
public static function getAvailableSystems();
|
||||
|
||||
/**
|
||||
* Create an ad system client
|
||||
* @param DoliDB $db Database handler
|
||||
* @param string $systemName Optional system name
|
||||
* @return AdSystemClientInterface|false
|
||||
*/
|
||||
public static function create(DoliDB $db, $systemName = null);
|
||||
|
||||
/**
|
||||
* Get currently configured system
|
||||
* @return string
|
||||
*/
|
||||
public static function getCurrentSystem();
|
||||
}
|
||||
```
|
||||
|
||||
**Usage Examples**:
|
||||
|
||||
```php
|
||||
// Create client for configured system
|
||||
$client = AdSystemFactory::create($db);
|
||||
|
||||
// Create specific client
|
||||
$googleClient = AdSystemFactory::create($db, 'googleads');
|
||||
$facebookClient = AdSystemFactory::create($db, 'facebookads');
|
||||
|
||||
// Get available systems
|
||||
$systems = AdSystemFactory::getAvailableSystems();
|
||||
// Returns: ['googleads' => 'Google Ads', 'facebookads' => 'Facebook Ads', ...]
|
||||
|
||||
// Get current system
|
||||
$current = AdSystemFactory::getCurrentSystem();
|
||||
// Returns: 'googleads' (or configured system)
|
||||
```
|
||||
|
||||
### 4. Report Class
|
||||
|
||||
Manages report data and persistence.
|
||||
|
||||
|
||||
**Properties**:
|
||||
|
||||
```php
|
||||
class Report extends CommonObject
|
||||
{
|
||||
public $ad_system_data; // JSON string of campaign data
|
||||
public $ad_system_type; // 'googleads', 'facebookads', 'microsoftads'
|
||||
public $claude_analysis; // JSON string of AI analysis
|
||||
public $date_start; // Report period start
|
||||
public $date_end; // Report period end
|
||||
// ... other properties
|
||||
}
|
||||
```
|
||||
|
||||
**Key Features**:
|
||||
- Handles both old and new database schemas
|
||||
- Automatic ref generation with format `ADCL[YYMMDD][NNNN]`
|
||||
|
||||
### 5. Claude AI Analyzer
|
||||
|
||||
Handles AI-powered analysis of campaign data.
|
||||
|
||||
|
||||
**Configuration**:
|
||||
- `MOKODOLIADINSIGHTS_CLAUDE_API_KEY`
|
||||
- `MOKODOLIADINSIGHTS_CLAUDE_MODEL`
|
||||
|
||||
## Data Flow
|
||||
|
||||
### Report Generation Flow
|
||||
|
||||
```
|
||||
1. User triggers report generation
|
||||
↓
|
||||
2. System reads configuration to determine active ad system
|
||||
↓
|
||||
3. AdSystemFactory::create() instantiates appropriate client
|
||||
↓
|
||||
4. Client->fetchCampaignData() retrieves data from API
|
||||
↓
|
||||
5. Data is validated and normalized
|
||||
↓
|
||||
6. ClaudeAnalyzer->analyze() sends data to Claude AI
|
||||
↓
|
||||
7. AI returns insights and recommendations
|
||||
↓
|
||||
8. Report object created with:
|
||||
- ad_system_data (campaign metrics)
|
||||
- ad_system_type (platform identifier)
|
||||
- claude_analysis (AI insights)
|
||||
↓
|
||||
9. Report saved to database
|
||||
↓
|
||||
10. User sees comprehensive report with insights
|
||||
```
|
||||
|
||||
### Scheduled Task Flow
|
||||
|
||||
```
|
||||
1. Cron/Scheduled task triggers
|
||||
↓
|
||||
2. Check if auto-refresh is enabled
|
||||
↓
|
||||
3. Determine date range based on schedule (daily/weekly/monthly)
|
||||
↓
|
||||
4. Create ad system client via factory
|
||||
↓
|
||||
5. Fetch campaign data
|
||||
↓
|
||||
6. Analyze with Claude AI
|
||||
↓
|
||||
7. Create and save report
|
||||
↓
|
||||
8. Notify users (if configured)
|
||||
```
|
||||
|
||||
## Database Schema
|
||||
|
||||
### llx_mokodoliadinsights_report
|
||||
|
||||
Primary table for storing reports.
|
||||
|
||||
```sql
|
||||
CREATE TABLE llx_mokodoliadinsights_report(
|
||||
rowid integer AUTO_INCREMENT PRIMARY KEY NOT NULL,
|
||||
ref varchar(128) NOT NULL,
|
||||
label varchar(255),
|
||||
description text,
|
||||
date_report datetime NOT NULL,
|
||||
date_start datetime NOT NULL,
|
||||
date_end datetime NOT NULL,
|
||||
ad_system_data longtext, -- Campaign data JSON
|
||||
ad_system_type varchar(50) DEFAULT 'googleads' NOT NULL,
|
||||
claude_analysis longtext, -- AI analysis JSON
|
||||
metrics_summary text,
|
||||
status integer DEFAULT 0 NOT NULL,
|
||||
note_public text,
|
||||
note_private text,
|
||||
date_creation datetime NOT NULL,
|
||||
tms timestamp DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
|
||||
fk_user_creat integer NOT NULL,
|
||||
fk_user_modif integer,
|
||||
entity integer DEFAULT 1 NOT NULL,
|
||||
INDEX idx_mokodoliadinsights_report_ad_system_type (ad_system_type)
|
||||
) ENGINE=innodb;
|
||||
```
|
||||
|
||||
**Key Fields**:
|
||||
- `ad_system_data`: Stores JSON-encoded campaign data from any platform
|
||||
- `ad_system_type`: Identifies which platform the data came from
|
||||
- `claude_analysis`: Stores AI-generated insights
|
||||
- Index on `ad_system_type` for efficient filtering
|
||||
|
||||
## Configuration Management
|
||||
|
||||
### Configuration Keys
|
||||
|
||||
All configuration is stored in Dolibarr's `const` table:
|
||||
|
||||
**Ad System Selection**:
|
||||
- `MOKODOLIADINSIGHTS_AD_SYSTEM`: Current active platform
|
||||
|
||||
**Google Ads**:
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CLIENT_ID`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CLIENT_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_DEVELOPER_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_REFRESH_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_GOOGLEADS_CUSTOMER_ID`
|
||||
|
||||
**Facebook Ads**:
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_APP_ID`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_APP_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_ACCESS_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_FACEBOOKADS_ACCOUNT_ID`
|
||||
|
||||
**Microsoft Ads**:
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_CLIENT_ID`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_CLIENT_SECRET`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_DEVELOPER_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_REFRESH_TOKEN`
|
||||
- `MOKODOLIADINSIGHTS_MICROSOFTADS_ACCOUNT_ID`
|
||||
|
||||
**Claude AI**:
|
||||
- `MOKODOLIADINSIGHTS_CLAUDE_API_KEY`
|
||||
- `MOKODOLIADINSIGHTS_CLAUDE_MODEL`
|
||||
|
||||
**Report Settings**:
|
||||
- `MOKODOLIADINSIGHTS_AUTO_REFRESH`
|
||||
- `MOKODOLIADINSIGHTS_DEFAULT_DATE_RANGE`
|
||||
|
||||
**Scheduled Tasks** (new):
|
||||
- `MOKODOLIADINSIGHTS_SCHEDULED_FREQUENCY`: daily/weekly/monthly
|
||||
- `MOKODOLIADINSIGHTS_SCHEDULED_ENABLED`: 0/1
|
||||
|
||||
### Security
|
||||
|
||||
Sensitive credentials are stored with encryption:
|
||||
- Uses `setAsSecureKey()` in form setup
|
||||
- Dolibarr's encryption mechanism protects API keys
|
||||
- Never exposed in logs or error messages
|
||||
|
||||
## Extensibility
|
||||
|
||||
### Adding a New Ad Platform
|
||||
|
||||
To add support for a new advertising platform (e.g., LinkedIn Ads):
|
||||
|
||||
**1. Create Client Class**
|
||||
|
||||
```php
|
||||
// src/class/linkedinadsclient.class.php
|
||||
require_once __DIR__.'/adsystemclientinterface.class.php';
|
||||
|
||||
class LinkedInAdsClient implements AdSystemClientInterface
|
||||
{
|
||||
private $db;
|
||||
private $clientId;
|
||||
private $clientSecret;
|
||||
private $accessToken;
|
||||
|
||||
public function __construct(DoliDB $db)
|
||||
{
|
||||
global $conf;
|
||||
$this->db = $db;
|
||||
$this->clientId = getDolGlobalString('MOKODOLIADINSIGHTS_LINKEDIN_CLIENT_ID');
|
||||
$this->clientSecret = getDolGlobalString('MOKODOLIADINSIGHTS_LINKEDIN_CLIENT_SECRET');
|
||||
$this->accessToken = getDolGlobalString('MOKODOLIADINSIGHTS_LINKEDIN_ACCESS_TOKEN');
|
||||
}
|
||||
|
||||
public function getSystemName()
|
||||
{
|
||||
return 'linkedinads';
|
||||
}
|
||||
|
||||
public function getSystemDisplayName()
|
||||
{
|
||||
return 'LinkedIn Ads';
|
||||
}
|
||||
|
||||
public function isConfigured()
|
||||
{
|
||||
return !empty($this->clientId) && !empty($this->clientSecret) &&
|
||||
!empty($this->accessToken);
|
||||
}
|
||||
|
||||
public function fetchCampaignData($dateStart, $dateEnd)
|
||||
{
|
||||
// Implement LinkedIn Ads API call
|
||||
// Return standardized JSON format
|
||||
}
|
||||
|
||||
public function getError()
|
||||
{
|
||||
return $this->error;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**2. Register in Factory**
|
||||
|
||||
```php
|
||||
// In src/class/adsystemfactory.class.php
|
||||
public static function getAvailableSystems()
|
||||
{
|
||||
return array(
|
||||
'googleads' => 'Google Ads',
|
||||
'facebookads' => 'Facebook Ads',
|
||||
'microsoftads' => 'Microsoft Ads',
|
||||
'linkedinads' => 'LinkedIn Ads' // Add this
|
||||
);
|
||||
}
|
||||
|
||||
public static function create(DoliDB $db, $systemName = null)
|
||||
{
|
||||
// ... existing code ...
|
||||
|
||||
switch ($systemName) {
|
||||
// ... existing cases ...
|
||||
case 'linkedinads':
|
||||
require_once __DIR__.'/linkedinadsclient.class.php';
|
||||
return new LinkedInAdsClient($db);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**3. Add Configuration**
|
||||
|
||||
```php
|
||||
// In src/admin/setup.php
|
||||
$formSetup->newItem('LinkedInAdsSection')->setAsTitle();
|
||||
|
||||
$item = $formSetup->newItem('MOKODOLIADINSIGHTS_LINKEDIN_CLIENT_ID');
|
||||
$item->helpText = 'Your LinkedIn Ads Client ID';
|
||||
|
||||
$item = $formSetup->newItem('MOKODOLIADINSIGHTS_LINKEDIN_CLIENT_SECRET');
|
||||
$item->setAsSecureKey();
|
||||
$item->helpText = 'Your LinkedIn Ads Client Secret';
|
||||
|
||||
$item = $formSetup->newItem('MOKODOLIADINSIGHTS_LINKEDIN_ACCESS_TOKEN');
|
||||
$item->setAsSecureKey();
|
||||
$item->helpText = 'Your LinkedIn Ads Access Token';
|
||||
```
|
||||
|
||||
**4. Add Translations**
|
||||
|
||||
```
|
||||
// In src/langs/en_US/mokodoliadinsights.lang
|
||||
LinkedInAds = LinkedIn Ads
|
||||
LinkedInAdsSection = LinkedIn Ads Configuration
|
||||
MOKODOLIADINSIGHTS_LINKEDIN_CLIENT_ID = LinkedIn Client ID
|
||||
...
|
||||
```
|
||||
|
||||
**5. Update Documentation**
|
||||
|
||||
Add LinkedIn Ads to:
|
||||
- README files
|
||||
- Installation guide
|
||||
- This architecture document
|
||||
|
||||
That's it! The new platform is fully integrated.
|
||||
|
||||
## Performance Considerations
|
||||
|
||||
### Caching
|
||||
|
||||
- Campaign data is cached in the report table
|
||||
- No need to re-fetch for existing reports
|
||||
- Scheduled tasks can pre-generate reports
|
||||
|
||||
### API Rate Limits
|
||||
|
||||
Each platform has rate limits:
|
||||
- **Google Ads**: 15,000 operations per day
|
||||
- **Facebook Ads**: 200 calls per hour per user
|
||||
- **Microsoft Ads**: Varies by account type
|
||||
|
||||
The module handles rate limiting by:
|
||||
- Caching fetched data
|
||||
- Using scheduled tasks to spread API calls
|
||||
- Implementing retry logic with exponential backoff
|
||||
|
||||
### Database Performance
|
||||
|
||||
- Index on `ad_system_type` for filtering
|
||||
- Index on `date_report` for date-based queries
|
||||
- Longtext fields for large JSON payloads
|
||||
|
||||
## Security Architecture
|
||||
|
||||
### Credential Storage
|
||||
|
||||
- API keys stored encrypted via Dolibarr's security system
|
||||
- Never logged or displayed in UI
|
||||
- Transmitted only over HTTPS (recommended)
|
||||
|
||||
### Input Validation
|
||||
|
||||
- All user inputs sanitized
|
||||
- Date ranges validated
|
||||
- Platform selection validated against allowed values
|
||||
|
||||
### Output Encoding
|
||||
|
||||
- HTML output escaped
|
||||
- JSON properly encoded
|
||||
- XSS prevention throughout
|
||||
|
||||
### Permissions
|
||||
|
||||
Module defines granular permissions:
|
||||
- Read reports
|
||||
- Create/Update reports
|
||||
- Delete reports
|
||||
- Configure module
|
||||
|
||||
## Error Handling
|
||||
|
||||
### Graceful Degradation
|
||||
|
||||
- If API call fails, error is logged and user-friendly message shown
|
||||
- Reports can still be viewed even if new data can't be fetched
|
||||
- System continues to work if one platform is misconfigured
|
||||
|
||||
### Logging
|
||||
|
||||
Errors are logged to:
|
||||
- Dolibarr system log
|
||||
- Module-specific error properties
|
||||
- Database error fields
|
||||
|
||||
### User Feedback
|
||||
|
||||
- Clear error messages for configuration issues
|
||||
- Helpful hints for common problems
|
||||
- Links to documentation
|
||||
|
||||
## Testing Strategy
|
||||
|
||||
### Unit Testing
|
||||
|
||||
Test individual components:
|
||||
- Each ad client in isolation
|
||||
- Factory pattern logic
|
||||
- Report class methods
|
||||
|
||||
### Integration Testing
|
||||
|
||||
Test component interaction:
|
||||
- Factory creating correct clients
|
||||
- Clients returning valid data format
|
||||
- Reports storing data correctly
|
||||
|
||||
### End-to-End Testing
|
||||
|
||||
Test complete workflows:
|
||||
- Configure platform → Generate report
|
||||
- Switch platforms → Generate report
|
||||
- Scheduled task execution
|
||||
|
||||
## Future Enhancements
|
||||
|
||||
Potential architecture improvements:
|
||||
|
||||
1. **Multi-platform Reports**: Compare data across platforms
|
||||
2. **Data Warehouse**: Historical trend analysis
|
||||
3. **Real-time Updates**: WebSocket-based live data
|
||||
4. **Advanced Analytics**: Custom metrics and calculations
|
||||
5. **API Endpoints**: REST API for external access
|
||||
6. **Webhooks**: Event-driven updates
|
||||
|
||||
## Conclusion
|
||||
|
||||
The MokoDoliAdInsights architecture is:
|
||||
- **Flexible**: Easy to add new platforms
|
||||
- **Maintainable**: Clear separation of concerns
|
||||
- **Scalable**: Handles multiple platforms efficiently
|
||||
- **Secure**: Encrypted credentials and proper validation
|
||||
- **User-friendly**: Simple configuration and usage
|
||||
|
||||
The interface-based design with factory pattern provides a solid foundation for long-term growth and maintenance.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,192 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to the MokoDoliAdInsights module will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Changed
|
||||
- **Module picto**: Updated module icon to Font Awesome `rectangle-ad` (classic/solid) — `fa-rectangle-ad` — across the module descriptor, Report object, and all admin/page headers.
|
||||
|
||||
### Added
|
||||
- **Google Ads, Facebook Ads, Microsoft Ads services**: Migrated to `BaseAdService` subclasses in `src/services/` (previously legacy clients in `src/class/`). Each service now exposes `getConfigurationFields()`, `getAvailableMetrics()`, `getCapabilities()`, and full PHPDoc.
|
||||
- **Per-service admin tabs**: Every ad platform has its own configuration tab in the Dolibarr admin panel, rendered by the new `admin/service.php` page. Tabs are populated automatically from `AdSystemFactory::getAvailableSystems()` — no file edits needed when adding a new service.
|
||||
- **`admin/service.php`**: Generic per-service credential configuration page. Validates the `?service=` parameter against the factory whitelist, renders `getConfigurationFields()` via `FormSetup`, and shows a configured/not-configured status indicator.
|
||||
- **Video Advertising Services**: Two new ad platform integrations for video campaigns
|
||||
- **YouTube Ads** (`youtubeads`): Integrates with Google Ads API v17 for YouTube video campaigns. Exposes video-specific metrics: video views, view rate, average CPE, engagements, and video completion quartiles (Q1/Q2/Q3/full).
|
||||
- **TikTok Ads** (`tiktokads`): Integrates with TikTok for Business Marketing API v1.3. Exposes TikTok video metrics: video play actions, 2-second views, 6-second views, completion quartiles, and average video play duration per user.
|
||||
- Both services declare `video_metrics` and `video_completion_tracking` capabilities.
|
||||
- **Real Claude AI Analysis**: `ClaudeAnalyzer::analyzeData()` now makes live HTTP requests to the Anthropic Messages API (`api.anthropic.com/v1/messages`) instead of returning static mock data.
|
||||
- **Auto-Discovery Service Architecture**: Adding a new ad platform service no longer requires editing any existing file. `AdSystemFactory` is pure auto-discovery — no hardcoded registrations.
|
||||
- **Translation keys**: `ServiceSettingsPage`, `ServiceConfigured`, `ServiceNotConfigured` added.
|
||||
|
||||
### Changed
|
||||
- **`AdSystemFactory`**: Completely rewritten as pure auto-discovery. All hardcoded legacy client references and switch cases removed. `create()` and `getAvailableSystems()` are 100% driven by the filesystem scan of `src/services/`.
|
||||
- **`admin/setup.php`**: Removed all per-service credential sections. Now contains only global settings: active ad system selector, Claude AI, report settings, and scheduled task settings.
|
||||
- **`lib/mokodoliadinsights.lib.php`**: `mokodoliadinsightsAdminPrepareHead()` dynamically adds one tab per service from `AdSystemFactory::getAvailableSystems()`.
|
||||
|
||||
### Removed
|
||||
- `src/class/googleadsclient.class.php` — replaced by `src/services/google/GoogleAdsService.class.php`
|
||||
- `src/class/facebookadsclient.class.php` — replaced by `src/services/facebook/FacebookAdsService.class.php`
|
||||
- `src/class/microsoftadsclient.class.php` — replaced by `src/services/microsoft/MicrosoftAdsService.class.php`
|
||||
- `src/class/adsystemclientinterface.class.php` — superseded by `src/services/AdServiceInterface.class.php`
|
||||
|
||||
### Planned
|
||||
- Multi-platform concurrent reporting (view multiple ad systems simultaneously)
|
||||
- Live API integration for all services (currently placeholder mock data)
|
||||
- Advanced competitive analysis features
|
||||
- Custom report templates
|
||||
- Data export to CSV/Excel
|
||||
- Dashboard widgets for Dolibarr home
|
||||
|
||||
## [1.2.0] - 2026-03-02
|
||||
|
||||
### Added
|
||||
- **Scheduled Tasks**: Automated report generation using Dolibarr's cron system
|
||||
- Configurable frequency: daily, weekly, or monthly
|
||||
- Automatic date range calculation based on frequency
|
||||
- Runs in background without user interaction
|
||||
- **Report Types**: Support for different report categories
|
||||
- Program Reports: Standard campaign performance analysis
|
||||
- Competitive Analysis: Competitor insights and comparisons
|
||||
- General Reports: Flexible general-purpose reporting
|
||||
- **Configuration Options**:
|
||||
- Default report type selection
|
||||
- Scheduled task enable/disable
|
||||
- Frequency selection (daily/weekly/monthly)
|
||||
- Comprehensive scheduled task documentation
|
||||
- Translation support for new features
|
||||
|
||||
### Changed
|
||||
- Updated module descriptor to version 1.2.0
|
||||
- Enhanced Report class with report_type field
|
||||
- Improved admin configuration interface
|
||||
- Updated all language files with new translations
|
||||
|
||||
### Technical
|
||||
- New class: `ScheduledTask` for automated reporting
|
||||
- New database column: `report_type` with index
|
||||
- Cron job registered in module descriptor
|
||||
|
||||
## [1.1.0] - 2026-03-01
|
||||
|
||||
### Added
|
||||
- **Multi-Platform Support**: Extended beyond Google Ads
|
||||
- Facebook Ads integration
|
||||
- Microsoft Ads integration
|
||||
- Interface-based architecture for easy extensibility
|
||||
- **Factory Pattern**: Centralized client creation via `AdSystemFactory`
|
||||
- **Configuration UI**: Platform selection and credential management for all systems
|
||||
- Comprehensive architecture documentation
|
||||
- Installation and integration guides
|
||||
|
||||
### Changed
|
||||
- Added `ad_system_type` column to track platform source
|
||||
- Module name updated to "Ad Systems + Claude AI"
|
||||
- Enhanced README files for clarity
|
||||
|
||||
### Technical
|
||||
- New interface: `AdSystemClientInterface`
|
||||
- New classes:
|
||||
- `AdSystemFactory`
|
||||
- `FacebookAdsClient`
|
||||
- `MicrosoftAdsClient`
|
||||
- Updated `GoogleAdsClient` to implement interface
|
||||
- Database indexes added for performance
|
||||
|
||||
## [1.0.0] - 2026-01-16
|
||||
|
||||
### Added
|
||||
- Initial release of MokoDoliAdInsights
|
||||
- Google Ads API integration
|
||||
- Claude AI analysis integration
|
||||
- Report generation with AI insights
|
||||
- Dashboard for viewing reports
|
||||
- Admin configuration interface
|
||||
- Multi-entity support
|
||||
- Permission system
|
||||
- Translation support (English)
|
||||
- Documentation
|
||||
|
||||
### Features
|
||||
- Fetch Google Ads campaign data
|
||||
- AI-powered analysis via Claude
|
||||
- Generate comprehensive reports
|
||||
- View historical reports
|
||||
- Configurable date ranges
|
||||
- Secure credential storage
|
||||
|
||||
---
|
||||
|
||||
## Version History Summary
|
||||
|
||||
| Version | Date | Key Features |
|
||||
|---------|------|--------------|
|
||||
| 1.2.0 | 2026-03-02 | Scheduled tasks, report types, frequency options |
|
||||
| 1.1.0 | 2026-03-01 | Multi-platform support (Facebook, Microsoft) |
|
||||
| 1.0.0 | 2026-01-16 | Initial release with Google Ads + Claude AI |
|
||||
|
||||
## Upgrade Guide
|
||||
|
||||
### Upgrading to 1.2.0 from 1.1.0
|
||||
|
||||
1. **Backup**: Always backup your database before upgrading
|
||||
2. **Update Files**: Pull latest code or download new version
|
||||
3. **Run Migration**:
|
||||
```sql
|
||||
source htdocs/custom/mokodoliadinsights/sql/llx_mokodoliadinsights_report-1.2.0.sql
|
||||
```
|
||||
4. **Clear Cache**: Delete Dolibarr cache files
|
||||
5. **Test**: Generate a test report to verify functionality
|
||||
6. **Configure**: Set up scheduled tasks if desired
|
||||
|
||||
## Breaking Changes
|
||||
|
||||
### Version 1.2.0
|
||||
- None.
|
||||
|
||||
### Version 1.1.0
|
||||
- None.
|
||||
|
||||
## Known Issues
|
||||
|
||||
### Version 1.2.0
|
||||
- Scheduled tasks require Dolibarr cron to be properly configured
|
||||
- Large date ranges may exceed API rate limits
|
||||
- Competitive analysis features are basic (enhanced features planned)
|
||||
|
||||
### Version 1.1.0
|
||||
- API credentials must be configured for each platform separately
|
||||
- Only one platform can be active at a time
|
||||
- Platform switching requires changing configuration
|
||||
|
||||
## Support & Contributions
|
||||
|
||||
Found a bug? Have a feature request?
|
||||
- Create an issue: https://github.com/mokoconsulting-tech/MokoDoliAdInsights/issues
|
||||
- Submit a pull request with improvements
|
||||
- Check documentation: `/docs/`
|
||||
|
||||
## License
|
||||
|
||||
This module is licensed under the GNU General Public License v3.0.
|
||||
See LICENSE file for details.
|
||||
|
||||
---
|
||||
|
||||
**Note**: This changelog follows [Semantic Versioning](https://semver.org/).
|
||||
- **MAJOR** version: Incompatible API changes
|
||||
- **MINOR** version: Added functionality (backward compatible)
|
||||
- **PATCH** version: Bug fixes (backward compatible)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,323 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - use 600,000+ for development
|
||||
$this->numero = 600001;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Development Phase
|
||||
|
||||
Use module ID > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,310 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring the MokoDoliAdInsights module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 19.0 or higher
|
||||
- **PHP**: Version 7.4 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- curl (for API calls)
|
||||
- json
|
||||
- xml
|
||||
|
||||
### API Requirements
|
||||
|
||||
You'll need credentials for at least one advertising platform:
|
||||
|
||||
#### Google Ads API
|
||||
- Google Ads account with API access enabled
|
||||
- OAuth 2.0 credentials (Client ID, Client Secret)
|
||||
- Developer Token
|
||||
- Refresh Token
|
||||
- Customer ID
|
||||
|
||||
**How to get**: [Google Ads API Documentation](https://developers.google.com/google-ads/api/docs/get-started/overview)
|
||||
|
||||
#### Facebook Ads API
|
||||
- Facebook Developer account
|
||||
- Facebook App with Marketing API access
|
||||
- App ID and App Secret
|
||||
- Long-lived Access Token
|
||||
- Ad Account ID
|
||||
|
||||
**How to get**: [Facebook Marketing API Documentation](https://developers.facebook.com/docs/marketing-apis/get-started)
|
||||
|
||||
#### Microsoft Ads API
|
||||
- Microsoft Advertising account
|
||||
- Registered application
|
||||
- OAuth 2.0 credentials (Client ID, Client Secret)
|
||||
- Developer Token
|
||||
- Refresh Token
|
||||
- Account ID
|
||||
|
||||
**How to get**: [Microsoft Advertising API Documentation](https://docs.microsoft.com/en-us/advertising/guides/get-started)
|
||||
|
||||
#### Claude AI API
|
||||
- Anthropic account
|
||||
- Claude API key
|
||||
|
||||
**How to get**: [Claude AI API Documentation](https://docs.anthropic.com/)
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr's custom directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone the module repository:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliAdInsights.git mokodoliadinsights
|
||||
```
|
||||
|
||||
### 2. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/mokodoliadinsights
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/mokodoliadinsights -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/mokodoliadinsights -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 3. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find "MokoDoliAdInsights" module in the list
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 4. Configure the Module
|
||||
|
||||
After activation, configure your ad system and API credentials:
|
||||
|
||||
#### Select Ad System
|
||||
|
||||
1. Go to **MokoDoliAdInsights → Setup**
|
||||
2. In the **Ad System** dropdown, select your preferred platform:
|
||||
- Google Ads
|
||||
- Facebook Ads
|
||||
- Microsoft Ads
|
||||
|
||||
#### Configure Google Ads (if selected)
|
||||
|
||||
1. Enter your **Client ID**
|
||||
2. Enter your **Client Secret** (will be encrypted)
|
||||
3. Enter your **Developer Token** (will be encrypted)
|
||||
4. Enter your **Refresh Token** (will be encrypted)
|
||||
5. Enter your **Customer ID** (format: XXX-XXX-XXXX)
|
||||
|
||||
#### Configure Facebook Ads (if selected)
|
||||
|
||||
1. Enter your **App ID**
|
||||
2. Enter your **App Secret** (will be encrypted)
|
||||
3. Enter your **Access Token** (will be encrypted)
|
||||
4. Enter your **Account ID** (format: act_XXXXXXXXX)
|
||||
|
||||
#### Configure Microsoft Ads (if selected)
|
||||
|
||||
1. Enter your **Client ID**
|
||||
2. Enter your **Client Secret** (will be encrypted)
|
||||
3. Enter your **Developer Token** (will be encrypted)
|
||||
4. Enter your **Refresh Token** (will be encrypted)
|
||||
5. Enter your **Account ID**
|
||||
|
||||
#### Configure Claude AI
|
||||
|
||||
1. Enter your **Claude API Key** (will be encrypted)
|
||||
2. Select your preferred **Claude Model** (default: claude-3-5-sonnet-20241022)
|
||||
|
||||
#### Configure Report Settings
|
||||
|
||||
1. **Auto-refresh Data**: Enable to automatically fetch new data when generating reports
|
||||
2. **Default Date Range**: Select default period for reports (Last 7/30/90 Days, This Month, Last Month)
|
||||
|
||||
### 6. Verify Installation
|
||||
|
||||
Test the installation:
|
||||
|
||||
1. Go to **MokoDoliAdInsights → Dashboard**
|
||||
2. Click **Generate Report**
|
||||
3. Select a date range
|
||||
4. Click **Generate**
|
||||
|
||||
If configured correctly:
|
||||
- The system will fetch data from your selected ad platform
|
||||
- Claude AI will analyze the data
|
||||
- You'll see a comprehensive report with insights and recommendations
|
||||
|
||||
## Database Tables
|
||||
|
||||
The module creates the following database table:
|
||||
|
||||
- `llx_mokodoliadinsights_report`: Stores reports with campaign data and AI analysis
|
||||
|
||||
### Table Structure
|
||||
|
||||
```sql
|
||||
CREATE TABLE llx_mokodoliadinsights_report(
|
||||
rowid integer AUTO_INCREMENT PRIMARY KEY NOT NULL,
|
||||
ref varchar(128) NOT NULL,
|
||||
label varchar(255),
|
||||
description text,
|
||||
date_report datetime NOT NULL,
|
||||
date_start datetime NOT NULL,
|
||||
date_end datetime NOT NULL,
|
||||
ad_system_data longtext, -- Campaign data from ad platform
|
||||
ad_system_type varchar(50), -- Platform: googleads/facebookads/microsoftads
|
||||
claude_analysis longtext, -- AI analysis results
|
||||
metrics_summary text,
|
||||
status integer DEFAULT 0 NOT NULL,
|
||||
-- Additional fields...
|
||||
) ENGINE=innodb;
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
**Problem**: Module doesn't appear in the modules list
|
||||
|
||||
**Solutions**:
|
||||
- Clear Dolibarr cache: Delete `documents/install.lock` and refresh browser
|
||||
- Check file permissions (Apache/Nginx user needs read access)
|
||||
- Verify directory name is `mokodoliadinsights` (all lowercase)
|
||||
- Check PHP error logs: `/var/log/apache2/error.log` or `/var/log/nginx/error.log`
|
||||
|
||||
### Module Activation Fails
|
||||
|
||||
**Problem**: Error when clicking Activate
|
||||
|
||||
**Solutions**:
|
||||
- Check database connectivity in `conf/conf.php`
|
||||
- Verify database user has CREATE TABLE permissions
|
||||
- Check Dolibarr logs: `documents/dolibarr.log`
|
||||
- Ensure no syntax errors: `php -l core/modules/modMokoDoliAdInsights.class.php`
|
||||
|
||||
### API Connection Errors
|
||||
|
||||
**Problem**: "Error connecting to [Platform] API"
|
||||
|
||||
**Solutions**:
|
||||
|
||||
For **Google Ads**:
|
||||
- Verify OAuth 2.0 credentials are correct
|
||||
- Ensure Developer Token is approved
|
||||
- Check Customer ID format (XXX-XXX-XXXX)
|
||||
- Verify API access is enabled in Google Ads account
|
||||
|
||||
For **Facebook Ads**:
|
||||
- Verify App has Marketing API permissions
|
||||
- Ensure Access Token hasn't expired
|
||||
- Check Ad Account ID format (act_XXXXXXXXX)
|
||||
- Verify you have access to the specified ad account
|
||||
|
||||
For **Microsoft Ads**:
|
||||
- Verify OAuth credentials are correct
|
||||
- Ensure Developer Token is valid
|
||||
- Check Account ID is correct
|
||||
- Verify API access is enabled
|
||||
|
||||
For **Claude AI**:
|
||||
- Verify API key is correct and active
|
||||
- Check if you have sufficient API credits
|
||||
- Ensure your plan supports the selected model
|
||||
|
||||
### Data Not Fetching
|
||||
|
||||
**Problem**: Report generates but shows no data
|
||||
|
||||
**Solutions**:
|
||||
- Verify date range has actual campaign data
|
||||
- Check if campaigns were active during selected period
|
||||
- Ensure ad account has campaigns
|
||||
- Review API rate limits (you may be throttled)
|
||||
- Check network connectivity and firewall settings
|
||||
|
||||
### Permission Errors
|
||||
|
||||
**Problem**: "Access forbidden" errors
|
||||
|
||||
**Solutions**:
|
||||
- Verify user has module permissions in Dolibarr
|
||||
- Check user belongs to correct group
|
||||
- Ensure module permissions are properly defined
|
||||
- Log in as administrator to test
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
### 1. Deactivate
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find "MokoDoliAdInsights" module
|
||||
3. Click **Deactivate**
|
||||
|
||||
### 2. Remove Files (Optional)
|
||||
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/mokodoliadinsights
|
||||
```
|
||||
|
||||
### 3. Remove Database Tables (Optional)
|
||||
|
||||
**Warning**: This will delete all reports and data!
|
||||
|
||||
```sql
|
||||
DROP TABLE llx_mokodoliadinsights_report;
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
After successful installation:
|
||||
|
||||
- Read the [Architecture Overview](architecture.md) to understand the system
|
||||
- Review the [Development Guide](development.md) if you plan to customize
|
||||
- See the [Adding Services guide](adding-services.md) to add more platforms
|
||||
- See [Usage Examples](../src/README.md#usage) in the main documentation
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Check Dolibarr logs: `documents/dolibarr.log`
|
||||
- Review PHP error logs
|
||||
- Create an issue in the [GitHub repository](https://github.com/mokoconsulting-tech/MokoDoliAdInsights/issues)
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
## Security Notes
|
||||
|
||||
- API credentials are stored encrypted in the database
|
||||
- Use HTTPS for production installations
|
||||
- Restrict file permissions appropriately
|
||||
- Keep API keys secret and never commit them to version control
|
||||
- Regularly update the module and Dolibarr core
|
||||
- Review the [Security Policy](SECURITY) for best practices
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,222 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Quick Start: Adding a New Ad Platform
|
||||
|
||||
This is a condensed guide for experienced developers. For detailed explanations, see [adding-services.md](adding-services.md).
|
||||
|
||||
## 1. Copy Template (2 minutes)
|
||||
|
||||
```bash
|
||||
cd src/services/
|
||||
cp -r examples/ yourplatform/
|
||||
cd yourplatform/
|
||||
mv ExampleAdService.class.php YourPlatformService.class.php
|
||||
```
|
||||
|
||||
## 2. Update Service Class (10 minutes)
|
||||
|
||||
Edit `YourPlatformService.class.php`:
|
||||
|
||||
```php
|
||||
class YourPlatformService extends BaseAdService
|
||||
{
|
||||
public function __construct(DoliDB $db)
|
||||
{
|
||||
$this->serviceId = 'your_platform';
|
||||
$this->serviceName = 'Your Platform';
|
||||
$this->provider = 'company_name';
|
||||
parent::__construct($db);
|
||||
}
|
||||
|
||||
protected function loadConfiguration()
|
||||
{
|
||||
$this->config = array(
|
||||
'api_key' => getDolGlobalString('MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY'),
|
||||
'api_secret' => getDolGlobalString('MOKODOLIADINSIGHTS_YOURPLATFORM_API_SECRET'),
|
||||
);
|
||||
}
|
||||
|
||||
public function isConfigured()
|
||||
{
|
||||
return $this->isConfigValueSet('api_key') &&
|
||||
$this->isConfigValueSet('api_secret');
|
||||
}
|
||||
|
||||
// Implement other required methods...
|
||||
}
|
||||
```
|
||||
|
||||
## 3. Add Configuration (5 minutes)
|
||||
|
||||
Edit `src/admin/setup.php`:
|
||||
|
||||
```php
|
||||
$formSetup->newItem('YourPlatformSection')->setAsTitle();
|
||||
|
||||
$item = $formSetup->newItem('MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY');
|
||||
$item->setAsSecureKey();
|
||||
$item->helpText = 'Your Platform API Key';
|
||||
|
||||
$item = $formSetup->newItem('MOKODOLIADINSIGHTS_YOURPLATFORM_API_SECRET');
|
||||
$item->setAsSecureKey();
|
||||
$item->helpText = 'Your Platform API Secret';
|
||||
```
|
||||
|
||||
## 4. Add Translations (2 minutes)
|
||||
|
||||
Edit `src/langs/en_US/mokodoliadinsights.lang`:
|
||||
|
||||
```
|
||||
YourPlatform = Your Platform
|
||||
YourPlatformSection = Your Platform Configuration
|
||||
MOKODOLIADINSIGHTS_YOURPLATFORM_API_KEY = API Key
|
||||
MOKODOLIADINSIGHTS_YOURPLATFORM_API_SECRET = API Secret
|
||||
```
|
||||
|
||||
## 5. Register Service (3 minutes)
|
||||
|
||||
Edit `src/class/adsystemfactory.class.php`:
|
||||
|
||||
```php
|
||||
public static function getAvailableSystems()
|
||||
{
|
||||
return array(
|
||||
// ... existing systems ...
|
||||
'your_platform' => 'Your Platform',
|
||||
);
|
||||
}
|
||||
|
||||
public static function create(DoliDB $db, $systemName = null)
|
||||
{
|
||||
switch ($systemName) {
|
||||
// ... existing cases ...
|
||||
case 'your_platform':
|
||||
require_once __DIR__.'/../services/yourplatform/YourPlatformService.class.php';
|
||||
return new YourPlatformService($db);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## 6. Test (5 minutes)
|
||||
|
||||
1. Configure credentials in Dolibarr
|
||||
2. Select your platform
|
||||
3. Generate test report
|
||||
4. Verify data
|
||||
|
||||
## Total Time: ~30 minutes
|
||||
|
||||
## Key Files
|
||||
|
||||
| File | Purpose |
|
||||
|------|---------|
|
||||
| `YourPlatformService.class.php` | Main service logic |
|
||||
| `admin/setup.php` | Configuration UI |
|
||||
| `langs/en_US/mokodoliadinsights.lang` | Translations |
|
||||
| `class/adsystemfactory.class.php` | Service registration |
|
||||
|
||||
## Common Patterns
|
||||
|
||||
### API Call with Error Handling
|
||||
|
||||
```php
|
||||
try {
|
||||
$ch = curl_init($apiUrl);
|
||||
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
|
||||
curl_setopt($ch, CURLOPT_HTTPHEADER, array(
|
||||
'X-API-Key: ' . $this->getConfigValue('api_key'),
|
||||
));
|
||||
|
||||
$response = curl_exec($ch);
|
||||
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
|
||||
curl_close($ch);
|
||||
|
||||
if ($httpCode !== 200) {
|
||||
$this->setError('API error: HTTP ' . $httpCode);
|
||||
return false;
|
||||
}
|
||||
|
||||
return json_decode($response, true);
|
||||
} catch (Exception $e) {
|
||||
$this->setError($e->getMessage());
|
||||
return false;
|
||||
}
|
||||
```
|
||||
|
||||
### Data Transformation
|
||||
|
||||
```php
|
||||
$campaigns = array();
|
||||
foreach ($apiData['items'] as $item) {
|
||||
$campaigns[] = array(
|
||||
'id' => $item['campaign_id'],
|
||||
'name' => $item['campaign_name'],
|
||||
'impressions' => (int)$item['metrics']['impressions'],
|
||||
'clicks' => (int)$item['metrics']['clicks'],
|
||||
'spend' => (float)$item['metrics']['cost'],
|
||||
);
|
||||
}
|
||||
|
||||
return $this->formatResponse($campaigns, $totals, $dateStart, $dateEnd);
|
||||
```
|
||||
|
||||
### OAuth Token Refresh
|
||||
|
||||
```php
|
||||
protected function getAccessToken()
|
||||
{
|
||||
$refreshToken = $this->getConfigValue('refresh_token');
|
||||
|
||||
$response = $this->makeOAuthRequest('/oauth/token', array(
|
||||
'grant_type' => 'refresh_token',
|
||||
'refresh_token' => $refreshToken,
|
||||
'client_id' => $this->getConfigValue('client_id'),
|
||||
'client_secret' => $this->getConfigValue('client_secret'),
|
||||
));
|
||||
|
||||
return $response['access_token'];
|
||||
}
|
||||
```
|
||||
|
||||
## Need Help?
|
||||
|
||||
- 📖 **Full Guide**: [adding-services.md](adding-services.md)
|
||||
- 📝 **Template**: [services/examples/ExampleAdService.class.php](../src/services/examples/ExampleAdService.class.php)
|
||||
- 🏗️ **Architecture**: [architecture.md](architecture.md)
|
||||
- 💬 **Questions**: Create an issue on GitHub
|
||||
|
||||
## Checklist
|
||||
|
||||
Before submitting:
|
||||
|
||||
- [ ] Service class extends `BaseAdService`
|
||||
- [ ] All required methods implemented
|
||||
- [ ] Configuration added to `setup.php`
|
||||
- [ ] Translations added to `.lang` file
|
||||
- [ ] Service registered in factory
|
||||
- [ ] Tested with real API credentials
|
||||
- [ ] Error handling implemented
|
||||
- [ ] Documentation created (`README.md` in service directory)
|
||||
- [ ] Code follows module standards
|
||||
- [ ] No security vulnerabilities introduced
|
||||
|
||||
## Pro Tips
|
||||
|
||||
1. **Start Simple**: Get basic data fetching working first
|
||||
2. **Use Existing Services**: Check Google/Facebook/Microsoft for patterns
|
||||
3. **Test Incrementally**: Test each method as you implement it
|
||||
4. **Handle Errors**: Always catch exceptions and set clear error messages
|
||||
5. **Document Quirks**: Note platform-specific limitations in comments
|
||||
6. **Rate Limiting**: Respect API rate limits from day one
|
||||
7. **Validate Data**: Check API responses before processing
|
||||
8. **Use Constants**: Define API URLs and defaults as class constants
|
||||
|
||||
Happy coding! 🚀
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliAdInsights/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAdInsights](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAdInsights) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,43 @@
|
||||
# MokoDoliArt
|
||||
|
||||
A Dolibarr module used to send proofs of art to clients for approval.
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,148 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Documentation Index
|
||||
|
||||
Welcome to the moko-platform Dolibarr Template documentation. This guide will help you navigate all available documentation resources.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Get started with installing the template
|
||||
- [Development Guide](development.md) - Learn how to develop Dolibarr modules
|
||||
- [Module ID Policy](module-id-policy.md) - Understand module ID assignment process
|
||||
- [Changelog](changelog.md) - Track version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For New Users
|
||||
|
||||
If you're new to this template, start here:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Configuration and setup
|
||||
- Troubleshooting common issues
|
||||
|
||||
2. **[Module ID Policy](module-id-policy.md)**
|
||||
- Understanding module IDs
|
||||
- Development vs. production IDs
|
||||
- How to request an official ID
|
||||
- Best practices
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're developing a module, these guides will help:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and organization
|
||||
- Module descriptor configuration
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
2. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Code standards
|
||||
- Pull request process
|
||||
- Commit message guidelines
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Installation Guide](installation.md) to set up the template, then review the [Development Guide](development.md) for building your module.
|
||||
|
||||
**Q: What module ID should I use?**
|
||||
A: Use an ID greater than 600,000 during development. See the [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
**Q: Where are the code examples?**
|
||||
A: The [Development Guide](development.md) contains numerous code examples and best practices.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
|
||||
### moko-platform
|
||||
|
||||
- [MokoConsulting Tech GitHub](https://github.com/mokoconsulting-tech)
|
||||
- Template Repository: [moko-platform-Template-Dolibarr](https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 600001; // Development module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/
|
||||
git clone repo-url
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Template Version**: 1.0.0
|
||||
- **Last Updated**: 2026-01-16
|
||||
- **Minimum Dolibarr Version**: 12.0
|
||||
- **PHP Version**: 7.4+
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- New to the template? Start with [Installation Guide](installation.md)
|
||||
- Ready to develop? Check out [Development Guide](development.md)
|
||||
- Need to request a module ID? Review [Module ID Policy](module-id-policy.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,70 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to this project template will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Added
|
||||
- Comprehensive README.md with project overview and usage instructions
|
||||
- Module ID policy documentation
|
||||
- Installation guide with detailed setup instructions
|
||||
- Development guide with best practices and examples
|
||||
- Contributing guidelines
|
||||
- Documentation structure following moko-platform
|
||||
|
||||
## [1.0.0] - 2026-01-16
|
||||
|
||||
### Added
|
||||
- Initial template structure for Dolibarr modules
|
||||
- Basic documentation framework
|
||||
- Module ID policy requiring issue-based requests
|
||||
- Support for temporary development IDs (600,000+)
|
||||
|
||||
---
|
||||
|
||||
## Template Usage Notes
|
||||
|
||||
When using this template for your module:
|
||||
|
||||
1. Copy this changelog to your project
|
||||
2. Update the version numbers as you develop
|
||||
3. Document all changes in the appropriate category:
|
||||
- **Added** for new features
|
||||
- **Changed** for changes in existing functionality
|
||||
- **Deprecated** for soon-to-be removed features
|
||||
- **Removed** for now removed features
|
||||
- **Fixed** for any bug fixes
|
||||
- **Security** for vulnerability fixes
|
||||
|
||||
Example entry:
|
||||
```markdown
|
||||
## [1.1.0] - 2026-02-15
|
||||
|
||||
### Added
|
||||
- New feature X for handling Y
|
||||
- Support for Z functionality
|
||||
|
||||
### Fixed
|
||||
- Bug in module activation
|
||||
- Permission check in admin page
|
||||
|
||||
### Changed
|
||||
- Updated module descriptor format
|
||||
- Improved error handling
|
||||
```
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/compare/v1.0.0...HEAD
|
||||
[1.0.0]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/releases/tag/v1.0.0
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,323 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - use 600,000+ for development
|
||||
$this->numero = 600001;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Development Phase
|
||||
|
||||
Use module ID > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,173 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring your Dolibarr module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 12.0 or higher
|
||||
- **PHP**: Version 7.4 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- gd or imagick
|
||||
- curl
|
||||
- json
|
||||
- xml
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr's custom directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone this template repository:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr.git yourmodule
|
||||
```
|
||||
|
||||
Replace `yourmodule` with your desired module name (lowercase, no spaces).
|
||||
|
||||
### 2. Rename and Configure
|
||||
|
||||
Navigate to the module directory:
|
||||
|
||||
```bash
|
||||
cd yourmodule
|
||||
```
|
||||
|
||||
Rename the module descriptor file:
|
||||
|
||||
```bash
|
||||
mv modYourmodule.class.php modYourModuleName.class.php
|
||||
```
|
||||
|
||||
### 3. Configure Module ID
|
||||
|
||||
Open the module descriptor file and set a temporary module ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourModuleName.class.php
|
||||
$this->numero = 600001; // Use a number > 600,000 for development
|
||||
```
|
||||
|
||||
**Important:** Before publishing, request an official module ID by creating an issue in the repository.
|
||||
|
||||
### 4. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 5. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find your module in the list
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 6. Configure Module Settings (if applicable)
|
||||
|
||||
After activation:
|
||||
|
||||
1. Go to **Home → Setup → Modules/Applications**
|
||||
2. Click on your module name to access its configuration page
|
||||
3. Configure any required settings
|
||||
4. Save changes
|
||||
|
||||
## Database Setup
|
||||
|
||||
If your module requires database tables:
|
||||
|
||||
### Automatic Setup
|
||||
|
||||
The module descriptor can handle automatic table creation during activation. Ensure your SQL files are in the `sql/` directory:
|
||||
|
||||
```
|
||||
sql/
|
||||
├── llx_yourmodule_table.sql
|
||||
└── llx_yourmodule_table.key.sql
|
||||
```
|
||||
|
||||
### Manual Setup
|
||||
|
||||
Alternatively, run SQL scripts manually:
|
||||
|
||||
```bash
|
||||
mysql -u username -p database_name < sql/llx_yourmodule_table.sql
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Clear Dolibarr cache: Delete `/documents/install.lock` and refresh
|
||||
- Check file permissions
|
||||
- Verify PHP syntax errors: `php -l modYourModuleName.class.php`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure Apache/Nginx user has read access to all module files
|
||||
- Check `conf.php` file permissions in Dolibarr root
|
||||
|
||||
### Database Errors
|
||||
|
||||
- Verify database credentials in Dolibarr's `conf/conf.php`
|
||||
- Check SQL file syntax
|
||||
- Ensure database user has CREATE TABLE permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find your module and click **Deactivate**
|
||||
3. Optionally, remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
```
|
||||
|
||||
**Note:** Deactivating the module does not remove database tables. To remove data:
|
||||
|
||||
```sql
|
||||
DROP TABLE llx_yourmodule_table;
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Review the [Development Guide](development.md) to start customizing your module
|
||||
- Check the [Module ID Policy](module-id-policy.md) before distribution
|
||||
- Read the [Changelog](changelog.md) for version history
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Create an issue in the repository
|
||||
- Check Dolibarr logs: `/documents/dolibarr.log`
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliArt/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliArt](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliArt) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,28 @@
|
||||
# MokoDoliAuth
|
||||
|
||||
A Dolibarr authentication suite
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAuth) |
|
||||
|
||||
---
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAuth](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAuth) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliAuth/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliAuth](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliAuth) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,50 @@
|
||||
# MokoDoliCare
|
||||
|
||||
A childcare management software built on Dolibarr.
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
| [quick start](quick-start.-.-) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [admin guide](admin-guide.-.-) | ← [Home](Home) |
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [family management](family-management.-.-) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [remote checkin](remote-checkin.-.-) | ← [Home](Home) |
|
||||
| [roadmap](roadmap) | ← [Home](Home) |
|
||||
| [troubleshooting](troubleshooting) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
| [user guide](user-guide.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,317 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Documentation Index
|
||||
|
||||
Welcome to the MokoDoliCare Childcare Management Module documentation. This comprehensive guide will help you install, configure, use, and maintain the module.
|
||||
|
||||
## Quick Links
|
||||
|
||||
### Getting Started
|
||||
- [Quick Start Guide](quick-start.md) - **⚡ Get up and running in 10 minutes**
|
||||
- [Installation Guide](installation.md) - Detailed installation and setup instructions
|
||||
- [Module ID Policy](module-id-policy.md) - Understand module ID assignment process
|
||||
|
||||
### User Documentation
|
||||
- [User Guide](user-guide.md) - **📖 Complete guide for daily operations**
|
||||
- [Remote Check-In Guide](remote-checkin.md) - **📱 Tablet check-in and payroll time clock**
|
||||
- [Family Management Guide](family-management.md) - **👨👩👧👦 Managing families and linking children**
|
||||
- [Database Schema](database-schema.md) - Detailed database structure reference
|
||||
|
||||
### Administrator Documentation
|
||||
- [Admin Guide](admin-guide.md) - System configuration and management
|
||||
- [Troubleshooting Guide](troubleshooting.md) - Common issues and solutions
|
||||
|
||||
### Developer Documentation
|
||||
- [Development Guide](development.md) - Module development guidelines
|
||||
- [Changelog](changelog.md) - Version history and planned features
|
||||
- [Product Roadmap](roadmap.md) - **🗺️ Strategic vision and feature timeline**
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### 🚀 For New Users
|
||||
|
||||
If you're new to MokoDoliCare, **start here**:
|
||||
|
||||
1. **[Quick Start Guide](quick-start.md)** ⚡ **START HERE**
|
||||
- 10-minute setup walkthrough
|
||||
- Add your first child
|
||||
- Record attendance
|
||||
- Schedule activities
|
||||
- Quick reference card
|
||||
|
||||
2. **[Installation Guide](installation.md)**
|
||||
- System requirements
|
||||
- Detailed installation instructions
|
||||
- Post-installation setup
|
||||
- Troubleshooting installation issues
|
||||
|
||||
3. **[User Guide](user-guide.md)**
|
||||
- Complete feature documentation
|
||||
- Child management workflows
|
||||
- Attendance tracking procedures
|
||||
- Activity planning and scheduling
|
||||
- Daily operational workflows
|
||||
- Tips and best practices
|
||||
|
||||
### 👥 For Daily Users
|
||||
|
||||
Essential guides for staff and teachers:
|
||||
|
||||
1. **[User Guide](user-guide.md)** - Your main reference
|
||||
- Child management
|
||||
- Attendance tracking
|
||||
- Activity scheduling
|
||||
- Reports and analytics
|
||||
- Daily workflows
|
||||
|
||||
2. **[Quick Start Guide](quick-start.md)** - Quick reference
|
||||
- Common tasks
|
||||
- Keyboard shortcuts
|
||||
- Quick reference card
|
||||
|
||||
3. **[Troubleshooting Guide](troubleshooting.md)** - When things go wrong
|
||||
- Common issues
|
||||
- Error messages
|
||||
- Quick fixes
|
||||
|
||||
### 🔧 For System Administrators
|
||||
|
||||
Complete system management documentation:
|
||||
|
||||
1. **[Admin Guide](admin-guide.md)** - Primary admin reference
|
||||
- Installation and configuration
|
||||
- User management and permissions
|
||||
- Security and compliance
|
||||
- Backup and recovery
|
||||
- Performance tuning
|
||||
- Maintenance procedures
|
||||
|
||||
2. **[Database Schema](database-schema.md)** - Technical reference
|
||||
- Complete table structures
|
||||
- Field descriptions
|
||||
- Relationships and foreign keys
|
||||
- Indexes and performance
|
||||
- Example queries
|
||||
|
||||
3. **[Troubleshooting Guide](troubleshooting.md)** - Problem solving
|
||||
- Installation issues
|
||||
- Database problems
|
||||
- Permission issues
|
||||
- Performance optimization
|
||||
- Diagnostic tools
|
||||
|
||||
### 💻 For Developers
|
||||
|
||||
If you're developing or customizing the module:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and architecture
|
||||
- Coding standards
|
||||
- Security best practices
|
||||
- Database operations
|
||||
- API development
|
||||
- Testing procedures
|
||||
|
||||
2. **[Database Schema](database-schema.md)**
|
||||
- Complete schema documentation
|
||||
- Field definitions
|
||||
- Query examples
|
||||
- Performance considerations
|
||||
|
||||
3. **[Module ID Policy](module-id-policy.md)**
|
||||
- Understanding module IDs
|
||||
- Development vs. production IDs
|
||||
- How to request official ID
|
||||
|
||||
4. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Pull request process
|
||||
- Code review standards
|
||||
|
||||
### 📚 Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and planned features
|
||||
- **[Product Roadmap](roadmap.md)** - Strategic vision and feature timeline
|
||||
- **[README](README)** - Project overview
|
||||
- **[Database Schema](database-schema.md)** - Complete technical reference
|
||||
- **[Module ID Policy](module-id-policy.md)** - Module ID guidelines
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Quick Start Guide](quick-start.md) for a 10-minute walkthrough, or see [Installation Guide](installation.md) for detailed setup.
|
||||
|
||||
**Q: How do I add a child?**
|
||||
A: See [User Guide - Child Management](user-guide.md#child-management) for step-by-step instructions.
|
||||
|
||||
**Q: How do I record attendance?**
|
||||
A: See [User Guide - Attendance Tracking](user-guide.md#attendance-tracking) for daily attendance procedures.
|
||||
|
||||
**Q: Something's not working, what do I do?**
|
||||
A: Check the [Troubleshooting Guide](troubleshooting.md) for common issues and solutions.
|
||||
|
||||
**Q: What module ID should I use?**
|
||||
A: Use an ID greater than 600,000 during development. See the [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I configure user permissions?**
|
||||
A: See [Admin Guide - User Management](admin-guide.md#user-management) for detailed permission setup.
|
||||
|
||||
**Q: Where's the database documentation?**
|
||||
A: See [Database Schema](database-schema.md) for complete table structures, fields, and relationships.
|
||||
|
||||
**Q: What features are planned for the future?**
|
||||
A: See the [Product Roadmap](roadmap.md) for our strategic vision and upcoming features.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: [Report bugs or request features](https://github.com/mokoconsulting-tech/MokoDoliCare/issues)
|
||||
- **Troubleshooting Guide**: [troubleshooting.md](troubleshooting.md) - Check here first!
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
- **Professional Support**: Contact [Moko Consulting](https://mokoconsulting.tech)
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
### MokoDoliCare Project
|
||||
|
||||
- [GitHub Repository](https://github.com/mokoconsulting-tech/MokoDoliCare)
|
||||
- [Issue Tracker](https://github.com/mokoconsulting-tech/MokoDoliCare/issues)
|
||||
- [MokoConsulting Tech](https://github.com/mokoconsulting-tech)
|
||||
- [Moko Consulting](https://mokoconsulting.tech)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 185065; // Official Dolibarr module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/
|
||||
git clone repo-url
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Documentation Overview
|
||||
|
||||
### Complete Documentation Set
|
||||
|
||||
| Document | Purpose | Audience | Length |
|
||||
|----------|---------|----------|--------|
|
||||
| [Quick Start Guide](quick-start.md) | Get running in 10 minutes | New users | 10 min read |
|
||||
| [User Guide](user-guide.md) | Complete operational guide | Daily users | 45 min read |
|
||||
| [Remote Check-In Guide](remote-checkin.md) | Tablet check-in setup | All users | 20 min read |
|
||||
| [Family Management Guide](family-management.md) | Family management | All users | 25 min read |
|
||||
| [Admin Guide](admin-guide.md) | System management | Administrators | 60 min read |
|
||||
| [Installation Guide](installation.md) | Setup instructions | Administrators | 20 min read |
|
||||
| [Database Schema](database-schema.md) | Technical reference | Developers/DBAs | 30 min read |
|
||||
| [Troubleshooting Guide](troubleshooting.md) | Problem solving | All users | Reference |
|
||||
| [Development Guide](development.md) | Development guidelines | Developers | 45 min read |
|
||||
| [Module ID Policy](module-id-policy.md) | Module ID process | Developers | 15 min read |
|
||||
| [Product Roadmap](roadmap.md) | Strategic vision | All users | 20 min read |
|
||||
| [Changelog](changelog.md) | Version history | All users | 10 min read |
|
||||
|
||||
### Documentation Statistics
|
||||
|
||||
- **Total Pages**: 12 comprehensive guides
|
||||
- **Total Content**: ~145+ pages of documentation
|
||||
- **Last Updated**: 2026-03-03
|
||||
- **Documentation Version**: 1.1.0
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Module Version**: 1.1.0
|
||||
- **Documentation Version**: 1.1.0
|
||||
- **Last Updated**: 2026-03-03
|
||||
- **Minimum Dolibarr Version**: 12.0
|
||||
- **PHP Version**: 7.4+
|
||||
- **Database**: MySQL 5.7+ / MariaDB 10.3+ / PostgreSQL 11+
|
||||
|
||||
---
|
||||
|
||||
## Quick Navigation by Task
|
||||
|
||||
### I want to...
|
||||
|
||||
**Install the module**
|
||||
→ Start: [Installation Guide](installation.md)
|
||||
→ Quick: [Quick Start Guide](quick-start.md)
|
||||
|
||||
**Learn how to use it**
|
||||
→ Read: [User Guide](user-guide.md)
|
||||
→ Quick: [Quick Start Guide](quick-start.md)
|
||||
|
||||
**Add children and track attendance**
|
||||
→ See: [User Guide - Child Management](user-guide.md#child-management)
|
||||
→ See: [User Guide - Attendance](user-guide.md#attendance-tracking)
|
||||
|
||||
**Configure the system**
|
||||
→ Read: [Admin Guide](admin-guide.md)
|
||||
→ Setup: [Admin Guide - Configuration](admin-guide.md#configuration)
|
||||
|
||||
**Understand the database**
|
||||
→ Read: [Database Schema](database-schema.md)
|
||||
|
||||
**Fix a problem**
|
||||
→ Check: [Troubleshooting Guide](troubleshooting.md)
|
||||
|
||||
**Develop or customize**
|
||||
→ Read: [Development Guide](development.md)
|
||||
→ Schema: [Database Schema](database-schema.md)
|
||||
|
||||
**Contribute to the project**
|
||||
→ Read: [Contributing Guidelines](CONTRIBUTING)
|
||||
→ Policy: [Module ID Policy](module-id-policy.md)
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- ⚡ **New user?** Start with [Quick Start Guide](quick-start.md) - 10 minutes!
|
||||
- 📖 **Daily user?** Read [User Guide](user-guide.md) for complete features
|
||||
- 🔧 **Administrator?** Check [Admin Guide](admin-guide.md) for configuration
|
||||
- 💻 **Developer?** Review [Development Guide](development.md) for code guidelines
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,966 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Administrator Guide
|
||||
|
||||
Complete guide for system administrators managing MokoDoliCare childcare module installation, configuration, and maintenance.
|
||||
|
||||
## Table of Contents
|
||||
|
||||
1. [System Requirements](#system-requirements)
|
||||
2. [Installation](#installation)
|
||||
3. [Configuration](#configuration)
|
||||
4. [User Management](#user-management)
|
||||
5. [Permissions and Security](#permissions-and-security)
|
||||
6. [Backup and Recovery](#backup-and-recovery)
|
||||
7. [Performance Tuning](#performance-tuning)
|
||||
8. [Troubleshooting](#troubleshooting)
|
||||
9. [Maintenance Tasks](#maintenance-tasks)
|
||||
|
||||
---
|
||||
|
||||
## System Requirements
|
||||
|
||||
### Minimum Requirements
|
||||
|
||||
| Component | Requirement |
|
||||
|-----------|-------------|
|
||||
| **Dolibarr** | Version 12.0 or higher |
|
||||
| **PHP** | Version 7.4 or higher (8.0+ recommended) |
|
||||
| **Database** | MySQL 5.7+ / MariaDB 10.3+ / PostgreSQL 11+ |
|
||||
| **Web Server** | Apache 2.4+ or Nginx 1.18+ |
|
||||
| **Disk Space** | 50 MB for module + data storage |
|
||||
| **Memory** | 256 MB PHP memory_limit minimum |
|
||||
|
||||
### Recommended Requirements
|
||||
|
||||
| Component | Recommendation |
|
||||
|-----------|----------------|
|
||||
| **PHP** | 8.1 or 8.2 |
|
||||
| **Database** | MariaDB 10.6+ |
|
||||
| **Memory** | 512 MB PHP memory_limit |
|
||||
| **CPU** | 2+ cores |
|
||||
| **Storage** | SSD for database |
|
||||
|
||||
### Required PHP Extensions
|
||||
|
||||
```bash
|
||||
# Check installed extensions
|
||||
php -m | grep -E "mysqli|pdo|gd|curl|json|xml|mbstring"
|
||||
```
|
||||
|
||||
Required extensions:
|
||||
- `mysqli` or `pgsql` - Database connectivity
|
||||
- `gd` or `imagick` - Image processing
|
||||
- `curl` - External communications
|
||||
- `json` - JSON handling
|
||||
- `xml` - XML processing
|
||||
- `mbstring` - Multi-byte string support
|
||||
|
||||
---
|
||||
|
||||
## Installation
|
||||
|
||||
### Pre-Installation Checklist
|
||||
|
||||
```bash
|
||||
# 1. Verify Dolibarr installation
|
||||
ls -la /path/to/dolibarr/htdocs/
|
||||
|
||||
# 2. Check custom directory exists and is writable
|
||||
mkdir -p /path/to/dolibarr/htdocs/custom
|
||||
chmod 755 /path/to/dolibarr/htdocs/custom
|
||||
|
||||
# 3. Verify database credentials
|
||||
mysql -u dolibarr_user -p dolibarr_db -e "SELECT VERSION();"
|
||||
|
||||
# 4. Check PHP version and extensions
|
||||
php -v
|
||||
php -m
|
||||
```
|
||||
|
||||
### Installation Methods
|
||||
|
||||
#### Method 1: From ZIP File (Recommended for Production)
|
||||
|
||||
1. Download the latest release ZIP
|
||||
2. Log into Dolibarr as administrator
|
||||
3. Navigate to **Home → Setup → Modules → Deploy External Module**
|
||||
4. Upload the ZIP file
|
||||
5. Wait for upload and extraction to complete
|
||||
6. Click **Activate** on the Childcare module
|
||||
|
||||
#### Method 2: From Git Repository (Recommended for Development)
|
||||
|
||||
```bash
|
||||
# Navigate to custom directory
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
|
||||
# Clone repository
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliCare.git childcare
|
||||
|
||||
# Copy module files from src/ to childcare/
|
||||
cp -r childcare/src/* childcare/
|
||||
|
||||
# Set permissions
|
||||
chown -R www-data:www-data childcare/
|
||||
find childcare/ -type d -exec chmod 755 {} \;
|
||||
find childcare/ -type f -exec chmod 644 {} \;
|
||||
|
||||
# Activate in Dolibarr
|
||||
# Home → Setup → Modules → Find "Childcare Management" → Activate
|
||||
```
|
||||
|
||||
#### Method 3: Manual Installation
|
||||
|
||||
```bash
|
||||
# 1. Extract module files
|
||||
unzip module_childcare-1.0.0.zip -d /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# 2. Set ownership
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# 3. Set permissions
|
||||
chmod -R 755 /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# 4. Activate via Dolibarr web interface
|
||||
```
|
||||
|
||||
### Post-Installation Verification
|
||||
|
||||
```bash
|
||||
# 1. Check database tables created
|
||||
mysql -u user -p database -e "SHOW TABLES LIKE 'llx_childcare%';"
|
||||
|
||||
# Expected output:
|
||||
# llx_childcare_activity
|
||||
# llx_childcare_attendance
|
||||
# llx_childcare_child
|
||||
|
||||
# 2. Check module files
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/core/modules/
|
||||
|
||||
# Expected: modMokoDoliCare.class.php
|
||||
|
||||
# 3. Verify module is active
|
||||
mysql -u user -p database -e "SELECT * FROM llx_const WHERE name = 'MAIN_MODULE_CHILDCARE';"
|
||||
|
||||
# Expected: value = '1'
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Configuration
|
||||
|
||||
### Module Configuration Page
|
||||
|
||||
**Access**: Home → Setup → Modules → Childcare Management → Setup
|
||||
|
||||
### Basic Configuration
|
||||
|
||||
#### Module Settings
|
||||
|
||||
| Setting | Options | Description |
|
||||
|---------|---------|-------------|
|
||||
| **Default Status** | Active/Inactive | Default status for new children |
|
||||
| **Attendance Required** | Yes/No | Require attendance record for active children |
|
||||
| **Auto-Generate References** | Yes/No | Automatically generate child/activity references |
|
||||
| **Reference Format** | CHILD###, C### | Format for auto-generated references |
|
||||
|
||||
#### Configuration Constants
|
||||
|
||||
Add to Dolibarr configuration if needed:
|
||||
|
||||
```php
|
||||
// In Home → Setup → Other Setup → System
|
||||
// Or directly in database
|
||||
|
||||
INSERT INTO llx_const (name, value, type, note, entity)
|
||||
VALUES
|
||||
('CHILDCARE_DEFAULT_STATUS', '1', 'chaine', 'Default child status', 1),
|
||||
('CHILDCARE_AUTO_REF', '1', 'chaine', 'Auto-generate references', 1),
|
||||
('CHILDCARE_REF_FORMAT', 'CHILD###', 'chaine', 'Reference number format', 1),
|
||||
('CHILDCARE_ATTENDANCE_REQUIRED', '1', 'chaine', 'Require daily attendance', 1);
|
||||
```
|
||||
|
||||
### Multi-Entity Configuration
|
||||
|
||||
For managing multiple facilities:
|
||||
|
||||
1. Enable multi-entity in Dolibarr:
|
||||
- Home → Setup → Other Setup → Multi-entity → Enable
|
||||
|
||||
2. Configure entity access:
|
||||
```sql
|
||||
-- Assign childcare module to specific entities
|
||||
UPDATE llx_childcare_child SET entity = 2 WHERE facility_id = 'FACILITY_B';
|
||||
```
|
||||
|
||||
3. User entity assignments:
|
||||
- Home → Users & Groups → Users → [User] → Entity tab
|
||||
- Assign users to appropriate entities
|
||||
|
||||
### Email Notification Settings
|
||||
|
||||
Configure email notifications (if implemented):
|
||||
|
||||
```php
|
||||
// Configuration constants for notifications
|
||||
'CHILDCARE_EMAIL_ATTENDANCE', '1' // Email daily attendance summary
|
||||
'CHILDCARE_EMAIL_INCIDENTS', '1' // Email incident reports
|
||||
'CHILDCARE_EMAIL_TEMPLATE', 'childcare' // Email template to use
|
||||
```
|
||||
|
||||
### Appearance Customization
|
||||
|
||||
#### Custom CSS
|
||||
|
||||
Create custom styles:
|
||||
|
||||
```bash
|
||||
# Create custom CSS file
|
||||
nano /path/to/dolibarr/htdocs/custom/childcare/css/childcare_custom.css
|
||||
```
|
||||
|
||||
```css
|
||||
/* Custom childcare styles */
|
||||
.childcare-alert-high {
|
||||
background-color: #ff6b6b;
|
||||
color: white;
|
||||
padding: 10px;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
.childcare-attendance-present {
|
||||
color: green;
|
||||
font-weight: bold;
|
||||
}
|
||||
```
|
||||
|
||||
#### Module Icon
|
||||
|
||||
Replace default icon:
|
||||
|
||||
```bash
|
||||
cp your_icon.png /path/to/dolibarr/htdocs/custom/childcare/img/object_childcare.png
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## User Management
|
||||
|
||||
### Creating Users
|
||||
|
||||
1. **Navigate**: Home → Users & Groups → New User
|
||||
2. **Fill in details**:
|
||||
- Login, Name, Email
|
||||
- Password (enforce strong passwords)
|
||||
- Employee/External
|
||||
3. **Save** and assign permissions
|
||||
|
||||
### User Roles and Permissions
|
||||
|
||||
#### Role: Administrator
|
||||
|
||||
**Recommended Permissions**:
|
||||
```
|
||||
Childcare Module:
|
||||
✓ Read child records
|
||||
✓ Create/Edit child records
|
||||
✓ Delete child records
|
||||
✓ Read attendance
|
||||
✓ Create/Edit attendance
|
||||
✓ Delete attendance
|
||||
✓ Read activities
|
||||
✓ Create/Edit activities
|
||||
✓ Delete activities
|
||||
✓ View reports
|
||||
✓ Export data
|
||||
|
||||
Other Modules:
|
||||
✓ User management (if needed)
|
||||
✓ System configuration (if needed)
|
||||
```
|
||||
|
||||
#### Role: Lead Teacher
|
||||
|
||||
**Recommended Permissions**:
|
||||
```
|
||||
Childcare Module:
|
||||
✓ Read child records
|
||||
✓ Create/Edit child records
|
||||
✗ Delete child records
|
||||
✓ Read attendance
|
||||
✓ Create/Edit attendance
|
||||
✗ Delete attendance
|
||||
✓ Read activities
|
||||
✓ Create/Edit activities
|
||||
✗ Delete activities
|
||||
✓ View reports
|
||||
✓ Export data
|
||||
```
|
||||
|
||||
#### Role: Teacher
|
||||
|
||||
**Recommended Permissions**:
|
||||
```
|
||||
Childcare Module:
|
||||
✓ Read child records
|
||||
✗ Create/Edit child records
|
||||
✗ Delete child records
|
||||
✓ Read attendance
|
||||
✓ Create/Edit attendance
|
||||
✗ Delete attendance
|
||||
✓ Read activities
|
||||
✗ Create/Edit activities
|
||||
✗ Delete activities
|
||||
✗ View reports
|
||||
✗ Export data
|
||||
```
|
||||
|
||||
#### Role: Office Staff
|
||||
|
||||
**Recommended Permissions**:
|
||||
```
|
||||
Childcare Module:
|
||||
✓ Read child records
|
||||
✓ Create/Edit child records
|
||||
✗ Delete child records
|
||||
✓ Read attendance
|
||||
✗ Create/Edit attendance
|
||||
✗ Delete attendance
|
||||
✓ Read activities
|
||||
✗ Create/Edit activities
|
||||
✗ Delete activities
|
||||
✓ View reports
|
||||
✓ Export data
|
||||
```
|
||||
|
||||
### Bulk User Permission Setup
|
||||
|
||||
```sql
|
||||
-- Grant all childcare permissions to a user group
|
||||
-- Example: Group ID 5 = Teachers
|
||||
|
||||
INSERT INTO llx_user_rights (fk_user, fk_id)
|
||||
SELECT u.rowid, 18506501 -- Read child records
|
||||
FROM llx_user u
|
||||
JOIN llx_usergroup_user ugu ON u.rowid = ugu.fk_user
|
||||
WHERE ugu.fk_usergroup = 5;
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Permissions and Security
|
||||
|
||||
### Permission Structure
|
||||
|
||||
Childcare module uses these permission IDs (based on module ID 185065):
|
||||
|
||||
| Permission | ID | Description |
|
||||
|------------|------|-------------|
|
||||
| Read child records | 18506501 | View child information |
|
||||
| Create/Edit child records | 18506502 | Add and modify children |
|
||||
| Delete child records | 18506503 | Remove child records |
|
||||
| Read attendance | 18506521 | View attendance records |
|
||||
| Create/Edit attendance | 18506522 | Record attendance |
|
||||
| Read activities | 18506531 | View activities |
|
||||
| Create/Edit activities | 18506532 | Manage activities |
|
||||
|
||||
### Security Best Practices
|
||||
|
||||
#### 1. Password Policy
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_authentication = 'dolibarr'; // Use Dolibarr auth
|
||||
$dolibarr_main_demo = '0'; // Disable demo mode
|
||||
```
|
||||
|
||||
Enforce strong passwords:
|
||||
- Minimum 12 characters
|
||||
- Mix of upper/lowercase, numbers, symbols
|
||||
- No dictionary words
|
||||
- Regular password changes (90 days)
|
||||
|
||||
#### 2. Session Security
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_force_https = '1'; // Force HTTPS
|
||||
$dolibarr_main_cookie_cryptkey = 'random_string'; // Secure cookie key
|
||||
```
|
||||
|
||||
#### 3. File Permissions
|
||||
|
||||
```bash
|
||||
# Secure configuration file
|
||||
chmod 600 /path/to/dolibarr/htdocs/conf/conf.php
|
||||
chown www-data:www-data /path/to/dolibarr/htdocs/conf/conf.php
|
||||
|
||||
# Secure module directory
|
||||
chmod 755 /path/to/dolibarr/htdocs/custom/childcare/
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
```
|
||||
|
||||
#### 4. Database Security
|
||||
|
||||
```sql
|
||||
-- Create dedicated database user with minimal privileges
|
||||
CREATE USER 'childcare_user'@'localhost' IDENTIFIED BY 'strong_password';
|
||||
GRANT SELECT, INSERT, UPDATE, DELETE ON dolibarr_db.llx_childcare_*
|
||||
TO 'childcare_user'@'localhost';
|
||||
FLUSH PRIVILEGES;
|
||||
```
|
||||
|
||||
#### 5. Backup Encryption
|
||||
|
||||
```bash
|
||||
# Backup with encryption
|
||||
mysqldump -u user -p dolibarr_db \
|
||||
llx_childcare_child \
|
||||
llx_childcare_attendance \
|
||||
llx_childcare_activity | \
|
||||
openssl enc -aes-256-cbc -salt -out childcare_backup_encrypted.sql.enc
|
||||
```
|
||||
|
||||
### Audit Trail
|
||||
|
||||
Enable detailed logging:
|
||||
|
||||
```sql
|
||||
-- Check who created/modified records
|
||||
SELECT
|
||||
c.ref,
|
||||
c.firstname,
|
||||
c.lastname,
|
||||
u1.login as created_by,
|
||||
c.date_creation,
|
||||
u2.login as modified_by,
|
||||
c.tms as last_modified
|
||||
FROM llx_childcare_child c
|
||||
LEFT JOIN llx_user u1 ON c.fk_user_creat = u1.rowid
|
||||
LEFT JOIN llx_user u2 ON c.fk_user_modif = u2.rowid
|
||||
ORDER BY c.tms DESC
|
||||
LIMIT 20;
|
||||
```
|
||||
|
||||
### GDPR Compliance
|
||||
|
||||
For European Union data protection:
|
||||
|
||||
1. **Right to Access**: Provide data export functionality
|
||||
2. **Right to Erasure**: Implement data deletion procedures
|
||||
3. **Data Minimization**: Only collect necessary information
|
||||
4. **Consent**: Document parental consent for data collection
|
||||
5. **Breach Notification**: Establish incident response procedures
|
||||
|
||||
#### Data Retention Policy
|
||||
|
||||
```sql
|
||||
-- Archive old attendance records (older than 3 years)
|
||||
CREATE TABLE llx_childcare_attendance_archive LIKE llx_childcare_attendance;
|
||||
|
||||
INSERT INTO llx_childcare_attendance_archive
|
||||
SELECT * FROM llx_childcare_attendance
|
||||
WHERE attendance_date < DATE_SUB(CURDATE(), INTERVAL 3 YEAR);
|
||||
|
||||
-- After verification, delete from main table
|
||||
DELETE FROM llx_childcare_attendance
|
||||
WHERE attendance_date < DATE_SUB(CURDATE(), INTERVAL 3 YEAR);
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Backup and Recovery
|
||||
|
||||
### Backup Strategy
|
||||
|
||||
#### Daily Backups
|
||||
|
||||
```bash
|
||||
#!/bin/bash
|
||||
# /usr/local/bin/childcare_daily_backup.sh
|
||||
|
||||
BACKUP_DIR="/backups/childcare"
|
||||
DATE=$(date +%Y%m%d_%H%M%S)
|
||||
DB_NAME="dolibarr_db"
|
||||
DB_USER="backup_user"
|
||||
DB_PASS="backup_password"
|
||||
|
||||
# Create backup directory
|
||||
mkdir -p "$BACKUP_DIR"
|
||||
|
||||
# Backup database tables
|
||||
mysqldump -u $DB_USER -p$DB_PASS $DB_NAME \
|
||||
llx_childcare_child \
|
||||
llx_childcare_attendance \
|
||||
llx_childcare_activity \
|
||||
> "$BACKUP_DIR/childcare_db_$DATE.sql"
|
||||
|
||||
# Backup module files
|
||||
tar -czf "$BACKUP_DIR/childcare_files_$DATE.tar.gz" \
|
||||
/path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Compress backup
|
||||
gzip "$BACKUP_DIR/childcare_db_$DATE.sql"
|
||||
|
||||
# Keep only last 30 days
|
||||
find "$BACKUP_DIR" -name "childcare_*" -mtime +30 -delete
|
||||
|
||||
echo "Backup completed: $DATE"
|
||||
```
|
||||
|
||||
#### Weekly Full Backup
|
||||
|
||||
```bash
|
||||
#!/bin/bash
|
||||
# Weekly full system backup including Dolibarr
|
||||
|
||||
BACKUP_DIR="/backups/weekly"
|
||||
DATE=$(date +%Y%m%d)
|
||||
|
||||
# Full database backup
|
||||
mysqldump -u root -p --all-databases > "$BACKUP_DIR/full_db_$DATE.sql"
|
||||
|
||||
# Full Dolibarr backup
|
||||
tar -czf "$BACKUP_DIR/dolibarr_full_$DATE.tar.gz" /path/to/dolibarr/
|
||||
|
||||
# Keep 8 weeks
|
||||
find "$BACKUP_DIR" -mtime +56 -delete
|
||||
```
|
||||
|
||||
#### Automated Backup with Cron
|
||||
|
||||
```bash
|
||||
# Edit crontab
|
||||
crontab -e
|
||||
|
||||
# Add backup schedules
|
||||
# Daily backup at 2 AM
|
||||
0 2 * * * /usr/local/bin/childcare_daily_backup.sh >> /var/log/childcare_backup.log 2>&1
|
||||
|
||||
# Weekly backup on Sundays at 3 AM
|
||||
0 3 * * 0 /usr/local/bin/weekly_full_backup.sh >> /var/log/weekly_backup.log 2>&1
|
||||
```
|
||||
|
||||
### Recovery Procedures
|
||||
|
||||
#### Restore from Backup
|
||||
|
||||
```bash
|
||||
# 1. Stop web server
|
||||
sudo systemctl stop apache2 # or nginx
|
||||
|
||||
# 2. Restore database
|
||||
gunzip childcare_db_20260219_020000.sql.gz
|
||||
mysql -u root -p dolibarr_db < childcare_db_20260219_020000.sql
|
||||
|
||||
# 3. Restore files
|
||||
tar -xzf childcare_files_20260219_020000.tar.gz -C /
|
||||
|
||||
# 4. Fix permissions
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# 5. Restart web server
|
||||
sudo systemctl start apache2
|
||||
```
|
||||
|
||||
#### Disaster Recovery
|
||||
|
||||
Full system recovery:
|
||||
|
||||
```bash
|
||||
# 1. Restore Dolibarr
|
||||
tar -xzf dolibarr_full_20260219.tar.gz -C /
|
||||
|
||||
# 2. Restore full database
|
||||
mysql -u root -p < full_db_20260219.sql
|
||||
|
||||
# 3. Verify module activation
|
||||
mysql -u root -p dolibarr_db -e "SELECT * FROM llx_const WHERE name='MAIN_MODULE_CHILDCARE';"
|
||||
|
||||
# 4. Test functionality
|
||||
# Log in and verify childcare module works
|
||||
```
|
||||
|
||||
### Testing Backups
|
||||
|
||||
**Monthly backup testing**:
|
||||
|
||||
```bash
|
||||
# 1. Restore to test environment
|
||||
# 2. Verify data integrity
|
||||
# 3. Test key functions
|
||||
# 4. Document results
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Performance Tuning
|
||||
|
||||
### Database Optimization
|
||||
|
||||
#### Index Optimization
|
||||
|
||||
```sql
|
||||
-- Check index usage
|
||||
SELECT
|
||||
TABLE_NAME,
|
||||
INDEX_NAME,
|
||||
CARDINALITY
|
||||
FROM information_schema.STATISTICS
|
||||
WHERE TABLE_SCHEMA = 'dolibarr_db'
|
||||
AND TABLE_NAME LIKE 'llx_childcare%'
|
||||
ORDER BY TABLE_NAME, INDEX_NAME;
|
||||
|
||||
-- Add missing indexes if needed
|
||||
ALTER TABLE llx_childcare_attendance
|
||||
ADD INDEX idx_attendance_child_date (fk_child, attendance_date);
|
||||
```
|
||||
|
||||
#### Query Performance
|
||||
|
||||
```sql
|
||||
-- Analyze slow queries
|
||||
EXPLAIN SELECT * FROM llx_childcare_attendance
|
||||
WHERE attendance_date >= DATE_SUB(CURDATE(), INTERVAL 30 DAY);
|
||||
|
||||
-- Optimize tables periodically
|
||||
OPTIMIZE TABLE llx_childcare_child;
|
||||
OPTIMIZE TABLE llx_childcare_attendance;
|
||||
OPTIMIZE TABLE llx_childcare_activity;
|
||||
```
|
||||
|
||||
### PHP Configuration
|
||||
|
||||
```ini
|
||||
# /etc/php/8.1/apache2/php.ini
|
||||
|
||||
memory_limit = 512M
|
||||
max_execution_time = 300
|
||||
post_max_size = 50M
|
||||
upload_max_filesize = 50M
|
||||
max_input_vars = 5000
|
||||
|
||||
# Enable OPcache
|
||||
opcache.enable=1
|
||||
opcache.memory_consumption=256
|
||||
opcache.max_accelerated_files=10000
|
||||
opcache.revalidate_freq=2
|
||||
```
|
||||
|
||||
### Web Server Optimization
|
||||
|
||||
#### Apache
|
||||
|
||||
```apache
|
||||
# /etc/apache2/sites-available/dolibarr.conf
|
||||
|
||||
<VirtualHost *:80>
|
||||
# Enable compression
|
||||
AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css text/javascript application/javascript
|
||||
|
||||
# Enable caching
|
||||
<IfModule mod_expires.c>
|
||||
ExpiresActive On
|
||||
ExpiresByType image/jpg "access plus 1 month"
|
||||
ExpiresByType image/jpeg "access plus 1 month"
|
||||
ExpiresByType image/gif "access plus 1 month"
|
||||
ExpiresByType image/png "access plus 1 month"
|
||||
ExpiresByType text/css "access plus 1 week"
|
||||
ExpiresByType application/javascript "access plus 1 week"
|
||||
</IfModule>
|
||||
</VirtualHost>
|
||||
```
|
||||
|
||||
#### Nginx
|
||||
|
||||
```nginx
|
||||
# /etc/nginx/sites-available/dolibarr
|
||||
|
||||
server {
|
||||
# Enable gzip compression
|
||||
gzip on;
|
||||
gzip_types text/css application/javascript text/javascript application/json;
|
||||
gzip_min_length 1000;
|
||||
|
||||
# Cache static files
|
||||
location ~* \.(jpg|jpeg|png|gif|ico|css|js)$ {
|
||||
expires 1M;
|
||||
add_header Cache-Control "public, immutable";
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Monitoring
|
||||
|
||||
#### Database Monitoring
|
||||
|
||||
```sql
|
||||
-- Monitor table sizes
|
||||
SELECT
|
||||
table_name,
|
||||
ROUND(((data_length + index_length) / 1024 / 1024), 2) AS "Size (MB)"
|
||||
FROM information_schema.TABLES
|
||||
WHERE table_schema = 'dolibarr_db'
|
||||
AND table_name LIKE 'llx_childcare%'
|
||||
ORDER BY (data_length + index_length) DESC;
|
||||
|
||||
-- Monitor slow queries
|
||||
SELECT * FROM mysql.slow_log
|
||||
WHERE sql_text LIKE '%llx_childcare%'
|
||||
ORDER BY start_time DESC
|
||||
LIMIT 10;
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
See detailed [Troubleshooting Guide](troubleshooting.md) for common issues and solutions.
|
||||
|
||||
### Quick Diagnostics
|
||||
|
||||
```bash
|
||||
# Check module is active
|
||||
mysql -u user -p database -e "SELECT value FROM llx_const WHERE name='MAIN_MODULE_CHILDCARE';"
|
||||
|
||||
# Check table existence
|
||||
mysql -u user -p database -e "SHOW TABLES LIKE 'llx_childcare%';"
|
||||
|
||||
# Check file permissions
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Check PHP errors
|
||||
tail -f /var/log/apache2/error.log
|
||||
# or
|
||||
tail -f /var/log/nginx/error.log
|
||||
|
||||
# Check Dolibarr logs
|
||||
tail -f /path/to/dolibarr/documents/dolibarr.log
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Maintenance Tasks
|
||||
|
||||
### Daily Tasks
|
||||
|
||||
- [ ] Monitor backup completion
|
||||
- [ ] Check error logs for issues
|
||||
- [ ] Verify system is accessible
|
||||
|
||||
### Weekly Tasks
|
||||
|
||||
- [ ] Review user activity logs
|
||||
- [ ] Check database performance
|
||||
- [ ] Test backup restoration
|
||||
- [ ] Review attendance completion rates
|
||||
|
||||
### Monthly Tasks
|
||||
|
||||
- [ ] Update module (if new version available)
|
||||
- [ ] Optimize database tables
|
||||
- [ ] Review and archive old data
|
||||
- [ ] Generate and review reports
|
||||
- [ ] Update documentation if needed
|
||||
|
||||
### Quarterly Tasks
|
||||
|
||||
- [ ] Review user permissions
|
||||
- [ ] Audit security settings
|
||||
- [ ] Performance review and tuning
|
||||
- [ ] Disaster recovery drill
|
||||
- [ ] User training refresher
|
||||
|
||||
---
|
||||
|
||||
## Support and Resources
|
||||
|
||||
### Documentation
|
||||
- [Installation Guide](installation.md)
|
||||
- [User Guide](user-guide.md)
|
||||
- [Database Schema](database-schema.md)
|
||||
- [Troubleshooting Guide](troubleshooting.md)
|
||||
|
||||
### External Resources
|
||||
- [Dolibarr Documentation](https://www.dolibarr.org/doc/)
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
- [GitHub Repository](https://github.com/mokoconsulting-tech/MokoDoliCare)
|
||||
|
||||
---
|
||||
|
||||
## CSV Import for Children
|
||||
|
||||
### Importing Children Records
|
||||
|
||||
The module supports CSV import for bulk enrollment of children records.
|
||||
|
||||
#### Accessing the Import Tool
|
||||
|
||||
1. Navigate to **Home → Import**
|
||||
2. Select **Import - Children** from the dataset dropdown
|
||||
3. Download the CSV template
|
||||
|
||||
#### CSV File Format
|
||||
|
||||
The CSV file should contain the following columns:
|
||||
|
||||
| Column | Required | Format | Example |
|
||||
|--------|----------|--------|---------|
|
||||
| Ref | Yes | Alphanumeric | CHILD001 |
|
||||
| FirstName | Yes | Text | Emma |
|
||||
| LastName | Yes | Text | Smith |
|
||||
| DateOfBirth | Yes | YYYY-MM-DD | 2020-05-15 |
|
||||
| Gender | No | Text | Female |
|
||||
| Allergies | No | Text | Peanuts, dairy |
|
||||
| MedicalNotes | No | Text | None |
|
||||
| EmergencyContact | No | Text | Parent: 555-1234 |
|
||||
| EnrollmentDate | No | YYYY-MM-DD | 2025-01-15 |
|
||||
| ThirdParty | No | Text | Smith Family |
|
||||
| Status | No | 0 or 1 | 1 |
|
||||
| Label | No | Text | Optional label |
|
||||
| NotePublic | No | Text | Public notes |
|
||||
| NotePrivate | No | Text | Private notes |
|
||||
|
||||
#### Import Process
|
||||
|
||||
1. **Prepare CSV File**: Create a CSV file with the required columns
|
||||
2. **Upload File**: Use the import wizard to upload your CSV file
|
||||
3. **Map Fields**: Verify field mappings (auto-detected from column names)
|
||||
4. **Validate**: Review validation errors and warnings
|
||||
5. **Import**: Execute the import
|
||||
6. **Review Results**: Check import summary and any errors
|
||||
|
||||
#### Example CSV
|
||||
|
||||
```csv
|
||||
Ref,FirstName,LastName,DateOfBirth,Gender,ThirdParty,Status
|
||||
CHILD001,Emma,Smith,2020-05-15,Female,Smith Family,1
|
||||
CHILD002,Noah,Johnson,2021-03-22,Male,Johnson Family,1
|
||||
CHILD003,Olivia,Williams,2019-11-08,Female,Williams Family,1
|
||||
```
|
||||
|
||||
#### Tips for Successful Import
|
||||
|
||||
- Ensure dates are in YYYY-MM-DD format
|
||||
- Status field: 1 = Active, 0 = Inactive
|
||||
- ThirdParty field should match existing third party names
|
||||
- Ref must be unique for each child
|
||||
- UTF-8 encoding recommended for special characters
|
||||
|
||||
---
|
||||
|
||||
## Auto-Invoice Generation
|
||||
|
||||
### Overview
|
||||
|
||||
The module can automatically generate invoices for families based on enrolled children and billing periods.
|
||||
|
||||
### Billing Models
|
||||
|
||||
The invoice generation service supports multiple billing models:
|
||||
|
||||
- **Monthly**: Fixed monthly fee per child
|
||||
- **Weekly**: Weekly billing cycle
|
||||
- **Daily**: Per-day attendance billing
|
||||
|
||||
### Accessing Invoice Generation
|
||||
|
||||
1. Navigate to **Childcare → Generate Invoices**
|
||||
2. Choose between:
|
||||
- **All Families**: Generate invoices for all families with active children
|
||||
- **Single Family**: Generate invoice for a specific family
|
||||
|
||||
### Generating Invoices
|
||||
|
||||
#### For All Families
|
||||
|
||||
1. Select **Billing Period** (Monthly/Weekly/Daily)
|
||||
2. Set **Period Start Date**
|
||||
3. Set **Period End Date**
|
||||
4. Click **Generate Invoices**
|
||||
|
||||
The system will:
|
||||
- Find all families with active children
|
||||
- Create one invoice per family
|
||||
- Add a line item for each child
|
||||
- Link invoice to the third party (family)
|
||||
|
||||
#### For a Single Family
|
||||
|
||||
1. Select the **Third Party (Family)**
|
||||
2. Select **Billing Period**
|
||||
3. Set **Period Start** and **Period End** dates
|
||||
4. Click **Generate Invoice**
|
||||
|
||||
### Invoice Line Items
|
||||
|
||||
Each invoice automatically includes:
|
||||
|
||||
**Child-Based Items**:
|
||||
- One line per active child
|
||||
- Description includes child's name
|
||||
- Default rates (configurable):
|
||||
- Monthly: €800
|
||||
- Weekly: €200
|
||||
- Daily: €40
|
||||
|
||||
**Family-Level Items** (optional):
|
||||
- Registration fees
|
||||
- Activity fees
|
||||
- Material fees
|
||||
- Other services
|
||||
|
||||
### Configuring Billing Rates
|
||||
|
||||
Rates can be customized in the invoice generation code or via configuration.
|
||||
|
||||
Default rates are set in `/services/InvoiceService.php`:
|
||||
|
||||
```php
|
||||
$default_rates = array(
|
||||
'monthly' => 800.00, // Monthly childcare fee
|
||||
'daily' => 40.00, // Daily rate
|
||||
'weekly' => 200.00 // Weekly rate
|
||||
);
|
||||
```
|
||||
|
||||
### Family Linking
|
||||
|
||||
**Important**: For invoice generation to work, children must be linked to a third party (family):
|
||||
|
||||
1. Edit the child record
|
||||
2. Set the **Family/Third Party** field
|
||||
3. Save the record
|
||||
|
||||
Children without a linked third party will not be included in automatic invoice generation.
|
||||
|
||||
### Invoice Workflow
|
||||
|
||||
1. **Generation**: Invoices are created in draft status
|
||||
2. **Review**: Admin reviews and adjusts if needed
|
||||
3. **Validation**: Validate invoice to lock it
|
||||
4. **Payment**: Process payments as usual in Dolibarr
|
||||
|
||||
### Best Practices
|
||||
|
||||
- Run invoice generation at the start of each billing period
|
||||
- Review generated invoices before validation
|
||||
- Set up automated reminders for unpaid invoices
|
||||
- Use consistent billing periods per family
|
||||
- Document special rates or discounts in invoice notes
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: 2026-03-03
|
||||
**Version**: 1.2.0-dev
|
||||
**For**: MokoDoliCare Childcare Management Module
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,230 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to MokoDoliCare (Childcare Management Module) will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Planned
|
||||
- Advanced reporting and analytics dashboard
|
||||
- Email notifications for parents
|
||||
- Multi-language support (Spanish, French, German)
|
||||
- Photo galleries for activities
|
||||
- Medical records and vaccination tracking
|
||||
- Meal planning and nutritional tracking
|
||||
- Invoice generation for childcare fees
|
||||
- Calendar integration with Google Calendar/Outlook
|
||||
- Mobile-responsive interface improvements
|
||||
- REST API endpoints for mobile app integration
|
||||
- Document management for child records
|
||||
- Staff scheduling and management
|
||||
- Emergency alert system
|
||||
|
||||
## [1.2.0] - 2026-03-03
|
||||
|
||||
### Added
|
||||
- **Official Module ID Assignment**
|
||||
- Module ID changed from 600001 (development) to 185065 (official)
|
||||
- Updated permission IDs to match new module number
|
||||
- Updated all documentation references
|
||||
|
||||
- **CSV Import Functionality**
|
||||
- Dolibarr-standard CSV import for children records
|
||||
- Support for bulk child enrollment
|
||||
- Field mapping configuration
|
||||
- Import validation and error handling
|
||||
|
||||
- **Auto-Invoice Generation**
|
||||
- Automatic invoice creation based on child records
|
||||
- Family-level billing via third party (fk_soc) linking
|
||||
- Support for child-based line items
|
||||
- Additional invoice items at family level
|
||||
- Configurable billing periods and rates
|
||||
|
||||
### Changed
|
||||
- Module ID: 600001 → 185065
|
||||
- Permission IDs updated to reflect new module number
|
||||
|
||||
### Removed
|
||||
- Legacy/sample files cleaned up
|
||||
|
||||
## [1.1.0] - 2026-03-03
|
||||
|
||||
### Added
|
||||
- **Remote Check-In System**
|
||||
- Parent/Guardian authentication with username and PIN
|
||||
- Secure PIN storage using bcrypt hashing
|
||||
- Tablet-optimized check-in interface
|
||||
- Digital signature capture using HTML5 Canvas
|
||||
- Touch-friendly UI with gradient design
|
||||
- 3-step check-in workflow (authenticate, select action, sign)
|
||||
- Session-based parent authentication
|
||||
- Support for multiple parents per child
|
||||
- Primary contact designation
|
||||
|
||||
- **Payroll Time Clock Functionality**
|
||||
- Accurate timestamp recording for check-in/check-out
|
||||
- Parent accountability tracking
|
||||
- Digital signature storage for both check-in and check-out
|
||||
- Audit trail showing which parent performed each action
|
||||
- Query examples for calculating billable hours
|
||||
|
||||
- **Parent Management Interface**
|
||||
- Parent/guardian CRUD operations
|
||||
- Parent list view with filtering
|
||||
- Parent card for creating/editing parent accounts
|
||||
- Relationship tracking (Mother, Father, Legal Guardian, Other)
|
||||
- Contact information management (email, phone)
|
||||
- Username uniqueness validation per entity
|
||||
|
||||
- **Database Schema Updates**
|
||||
- New table: `llx_childcare_parent` for parent credentials
|
||||
- Username and PIN hash storage
|
||||
- Relationship and contact information
|
||||
- Primary contact flag
|
||||
- Foreign key to child records
|
||||
- Updated table: `llx_childcare_attendance`
|
||||
- Added: `fk_parent_checkin` - tracks parent who checked in
|
||||
- Added: `fk_parent_checkout` - tracks parent who checked out
|
||||
- Added: `signature_checkin` - base64-encoded check-in signature
|
||||
- Added: `signature_checkout` - base64-encoded check-out signature
|
||||
- Foreign keys linking attendance to parent records
|
||||
- Indexes for performance on parent lookups
|
||||
|
||||
- **Security Enhancements**
|
||||
- XSS protection: sanitized form action URLs
|
||||
- Input validation for signatures (500KB size limit)
|
||||
- Secure PIN hashing with bcrypt
|
||||
- System user context for audit trail in public interface
|
||||
- Session-based authentication for tablet interface
|
||||
|
||||
- **Documentation**
|
||||
- Comprehensive remote check-in guide (9,000+ words)
|
||||
- Setup instructions for tablet devices
|
||||
- Security best practices
|
||||
- Troubleshooting section
|
||||
- SQL query examples for payroll reporting
|
||||
- Updated database schema documentation
|
||||
- Updated main README with feature highlights
|
||||
|
||||
- **Menu Items**
|
||||
- Parents submenu with list and create options
|
||||
- Tablet Check-In menu item (opens in new tab)
|
||||
- Integration with existing childcare menu structure
|
||||
|
||||
### Changed
|
||||
- Enhanced attendance tracking with parent accountability
|
||||
- Updated database schema version to 1.1.0
|
||||
- Improved documentation structure with new guides
|
||||
|
||||
### Technical Details
|
||||
- Added 30+ language translations for remote check-in features
|
||||
- Implemented HTML5 Canvas-based signature capture
|
||||
- Touch and mouse event support for signature pad
|
||||
- Base64 encoding for signature storage
|
||||
- Password verification using PHP's `password_verify()`
|
||||
- Session management for tablet check-in workflow
|
||||
|
||||
### Security
|
||||
- Fixed potential XSS vulnerabilities in form submissions
|
||||
- Implemented proper input sanitization throughout
|
||||
- Added signature size validation
|
||||
- Secure credential storage with industry-standard hashing
|
||||
|
||||
## [1.0.0] - 2025-02-19
|
||||
|
||||
### Added
|
||||
- **Child Management System**
|
||||
- Comprehensive child profiles with personal information
|
||||
- Date of birth and age tracking
|
||||
- Gender recording
|
||||
- Medical notes and allergy documentation
|
||||
- Emergency contact information
|
||||
- Enrollment date tracking
|
||||
- Active/Inactive status management
|
||||
- Public and private notes
|
||||
- Integration with Dolibarr user system
|
||||
|
||||
- **Attendance Tracking**
|
||||
- Daily attendance recording
|
||||
- Check-in and check-out time tracking
|
||||
- Attendance status indicators
|
||||
- Notes for daily activities and observations
|
||||
- Attendance history by child
|
||||
- Date-based filtering
|
||||
- User tracking for who recorded attendance
|
||||
|
||||
- **Activity Management**
|
||||
- Activity scheduling and planning
|
||||
- Activity type categorization (Learning, Play, Outdoor, Meals, Naps, Arts, Music, Story Time)
|
||||
- Description and notes for each activity
|
||||
- Date and time scheduling
|
||||
- Status tracking for activities
|
||||
- Reference system for activity identification
|
||||
|
||||
- **Database Schema**
|
||||
- `llx_childcare_child` - Child records table
|
||||
- `llx_childcare_attendance` - Attendance tracking table
|
||||
- `llx_childcare_activity` - Activity management table
|
||||
- Foreign key constraints for data integrity
|
||||
- Proper indexing for performance
|
||||
- Multi-entity support
|
||||
|
||||
- **Permission System**
|
||||
- Granular permissions for child records (read, write, delete)
|
||||
- Attendance permissions (read, write)
|
||||
- Activity permissions (read, write)
|
||||
- Role-based access control
|
||||
- Integration with Dolibarr permission system
|
||||
|
||||
- **User Interface**
|
||||
- Main dashboard with statistics
|
||||
- Top menu navigation
|
||||
- Children submenu with list and create options
|
||||
- Attendance tracking interface
|
||||
- Activities management interface
|
||||
- Responsive design following Dolibarr standards
|
||||
|
||||
- **Documentation**
|
||||
- Comprehensive README with feature overview
|
||||
- Installation instructions
|
||||
- Usage guide
|
||||
- Database schema documentation
|
||||
- Module structure documentation
|
||||
- Language file with all translations (English)
|
||||
|
||||
### Technical Details
|
||||
- Module ID: 600001 (development range)
|
||||
- Module Family: Human Resources (hr)
|
||||
- Module Position: 50
|
||||
- Minimum Dolibarr Version: 12.0
|
||||
- Minimum PHP Version: 7.4
|
||||
- Database Support: MySQL 5.7+, MariaDB 10.3+, PostgreSQL 9.6+
|
||||
- License: GPL v3 / MIT
|
||||
- Icon: FontAwesome child icon (fa-child)
|
||||
|
||||
### Development Setup
|
||||
- Modular architecture following Dolibarr standards
|
||||
- PSR-compatible code structure
|
||||
- Security-first approach with input sanitization
|
||||
- Database abstraction layer usage
|
||||
- Translation-ready infrastructure
|
||||
- Multi-entity support from the ground up
|
||||
|
||||
---
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/MokoDoliCare/compare/v1.1.0...HEAD
|
||||
[1.1.0]: https://github.com/mokoconsulting-tech/MokoDoliCare/compare/v1.0.0...v1.1.0
|
||||
[1.0.0]: https://github.com/mokoconsulting-tech/MokoDoliCare/releases/tag/v1.0.0
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,416 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── services/ # Service classes (NEW)
|
||||
│ ├── README.md # Services documentation
|
||||
│ ├── ExampleService.php # Service template
|
||||
│ ├── api/ # API services
|
||||
│ ├── integrations/ # Third-party integrations
|
||||
│ └── plugins/ # Plugin services
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - Official Dolibarr module ID
|
||||
$this->numero = 185065;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. Service Development
|
||||
|
||||
Services encapsulate reusable business logic and provide a clean separation between controllers and business operations.
|
||||
|
||||
#### Creating a Service
|
||||
|
||||
Services are stored in the `services/` directory:
|
||||
|
||||
```php
|
||||
<?php
|
||||
// services/NotificationService.php
|
||||
|
||||
if (!defined('MAIN_INC_PHP')) {
|
||||
die('Access denied');
|
||||
}
|
||||
|
||||
class NotificationService
|
||||
{
|
||||
private $db;
|
||||
private $user;
|
||||
|
||||
public function __construct($db, $user)
|
||||
{
|
||||
$this->db = $db;
|
||||
$this->user = $user;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send notification to parent
|
||||
*
|
||||
* @param int $parentId Parent ID
|
||||
* @param string $message Message content
|
||||
* @return array Result array
|
||||
*/
|
||||
public function sendNotification($parentId, $message)
|
||||
{
|
||||
try {
|
||||
// Business logic here
|
||||
return array(
|
||||
'success' => true,
|
||||
'data' => array('sent' => true)
|
||||
);
|
||||
} catch (Exception $e) {
|
||||
return array(
|
||||
'success' => false,
|
||||
'message' => $e->getMessage()
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
#### Using a Service
|
||||
|
||||
Include and use services in your pages:
|
||||
|
||||
```php
|
||||
<?php
|
||||
// In your page file
|
||||
dol_include_once('/childcare/services/NotificationService.php');
|
||||
|
||||
$notificationService = new NotificationService($db, $user);
|
||||
$result = $notificationService->sendNotification($parentId, $message);
|
||||
|
||||
if ($result['success']) {
|
||||
setEventMessages($langs->trans("NotificationSent"), null, 'mesgs');
|
||||
}
|
||||
```
|
||||
|
||||
#### Service Best Practices
|
||||
|
||||
1. **Return consistent formats**: Always return arrays with `success`, `data`, and `message` keys
|
||||
2. **Inject dependencies**: Pass required objects through constructor
|
||||
3. **Handle errors properly**: Use try-catch blocks and log errors
|
||||
4. **Document methods**: Use PHPDoc format for all public methods
|
||||
5. **Keep services focused**: Each service should have a single, well-defined purpose
|
||||
|
||||
See the [Services README](src-services-README) for comprehensive documentation and examples.
|
||||
|
||||
### 7. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Official Module ID
|
||||
|
||||
For public distribution, use your officially assigned module ID:
|
||||
|
||||
```php
|
||||
$this->numero = 185065; // MokoDoliCare official ID
|
||||
```
|
||||
|
||||
### Development Phase
|
||||
|
||||
For testing new features, you may use development IDs > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001; // For development only
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,291 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Family Management Guide
|
||||
|
||||
## Overview
|
||||
|
||||
The MokoDoliCare module uses Dolibarr's Third Party (Societe) system to manage families. Each child can be linked to a **Family** third party, which serves as a grouping mechanism for siblings and shared billing/communication.
|
||||
|
||||
## What is a Family?
|
||||
|
||||
A **Family** is a special type of third party in Dolibarr that represents a household or family unit. By linking children to families, you can:
|
||||
|
||||
- **Group siblings together** under one family unit
|
||||
- **Shared billing** - Invoice the family for multiple children
|
||||
- **Consolidated communication** - Send reports and notifications to the family
|
||||
- **Family contacts** - Manage multiple parent/guardian contacts under one family
|
||||
- **Simplified administration** - Update family information once for all children
|
||||
|
||||
## Creating a Family
|
||||
|
||||
### Method 1: During Child Creation
|
||||
|
||||
1. Navigate to **Childcare → Children → New Child**
|
||||
2. Fill in the child's basic information
|
||||
3. In the **Family Name** field, click the **+ icon** (plus sign)
|
||||
4. You'll be redirected to create a new third party:
|
||||
- **Third Party Name**: Enter the family name (e.g., "Smith Family", "Johnson Family")
|
||||
- **Third Party Type**: Select appropriate type or leave default
|
||||
- Add family address, phone, email
|
||||
- Add contacts (parents/guardians) under the Contacts tab
|
||||
5. Save the third party
|
||||
6. Return to the child creation form (it will be pre-selected)
|
||||
7. Complete and save the child record
|
||||
|
||||
### Method 2: Create Family First
|
||||
|
||||
1. Navigate to **Third Parties → New Third Party**
|
||||
2. Create the family:
|
||||
- **Name**: Family name (e.g., "Martinez Family")
|
||||
- **Type**: Customer, Prospect, or Neither (recommended: Neither for families)
|
||||
- **Address**: Family home address
|
||||
- **Phone/Email**: Primary family contact information
|
||||
3. Add parent/guardian contacts:
|
||||
- Go to the **Contacts/Addresses** tab
|
||||
- Click **Add Contact**
|
||||
- Enter parent/guardian information
|
||||
- Assign appropriate role (e.g., "Parent", "Guardian", "Emergency Contact")
|
||||
4. Save the family
|
||||
|
||||
5. Then create children linked to this family:
|
||||
- Navigate to **Childcare → Children → New Child**
|
||||
- Select the family from the **Family Name** dropdown
|
||||
- Complete child information
|
||||
|
||||
## Best Practices
|
||||
|
||||
### Naming Conventions
|
||||
|
||||
Use consistent naming for families:
|
||||
|
||||
**Recommended formats:**
|
||||
- `[LastName] Family` - e.g., "Johnson Family"
|
||||
- `[Parent1] and [Parent2] [LastName]` - e.g., "John and Mary Smith"
|
||||
- `The [LastName] Family` - e.g., "The Garcia Family"
|
||||
|
||||
**Avoid:**
|
||||
- Using individual parent names only (e.g., "John Smith") - use "Smith Family" instead
|
||||
- Special characters or abbreviations
|
||||
- Temporary or placeholder names
|
||||
|
||||
### Family Structure
|
||||
|
||||
For each family, set up:
|
||||
|
||||
1. **Primary Contact**: Main parent/guardian for billing and communication
|
||||
2. **Secondary Contact**: Second parent/guardian
|
||||
3. **Emergency Contacts**: Additional authorized pickup persons
|
||||
4. **Billing Address**: Where invoices should be sent
|
||||
5. **Email**: For digital communications and notifications
|
||||
|
||||
### Multiple Families
|
||||
|
||||
Some children may have separated parents or complex custody arrangements:
|
||||
|
||||
**Option 1: Single Family (Recommended for most cases)**
|
||||
- Create one family representing the primary household
|
||||
- Add both parents as contacts with appropriate roles
|
||||
- Use contact notes to document custody arrangements
|
||||
|
||||
**Option 2: Multiple Records**
|
||||
- For complex custody situations, you may create duplicate child records
|
||||
- Link each to a different family (one for each household)
|
||||
- Use status or notes to indicate which is primary
|
||||
|
||||
**Option 3: Shared Custody**
|
||||
- Create one family, add both parents as primary contacts
|
||||
- Document custody schedule in child notes
|
||||
- Use custom fields if available for detailed tracking
|
||||
|
||||
## Linking Children to Families
|
||||
|
||||
### During Child Creation
|
||||
|
||||
Simply select the family from the **Family Name** dropdown when creating a new child.
|
||||
|
||||
### Updating Existing Children
|
||||
|
||||
If you need to add family links to existing children:
|
||||
|
||||
1. Open the child's card
|
||||
2. Click **Edit** (modify)
|
||||
3. Select the family from the **Family Name** dropdown
|
||||
4. Save changes
|
||||
|
||||
**Note**: This feature requires running the database migration script. See [Migration Instructions](#migration-instructions) below.
|
||||
|
||||
## Family Reports and Views
|
||||
|
||||
### Viewing Family Children
|
||||
|
||||
1. Navigate to **Third Parties → Third Party List**
|
||||
2. Find and open the family
|
||||
3. View linked children in the childcare module section (if configured)
|
||||
|
||||
### Filtering by Family
|
||||
|
||||
In the children list:
|
||||
1. Use filters to show children by family
|
||||
2. Sort by family name to group siblings together
|
||||
|
||||
## Billing Families
|
||||
|
||||
Link invoices to the family third party:
|
||||
|
||||
1. Navigate to **Customers/Prospects → New Invoice**
|
||||
2. Select the **Family** as the third party
|
||||
3. Add line items for each child's services
|
||||
4. Use product references to indicate which child (e.g., "Childcare - Emma Smith")
|
||||
5. Send invoice to family contact
|
||||
|
||||
**Best Practice**: Create separate invoice lines for each child to provide clear breakdowns.
|
||||
|
||||
## Communication with Families
|
||||
|
||||
### Email Notifications
|
||||
|
||||
Configure email notifications to go to family contacts:
|
||||
- Check-in/check-out confirmations
|
||||
- Monthly attendance summaries
|
||||
- Activity updates
|
||||
- Billing reminders
|
||||
|
||||
### Parent Portal Access
|
||||
|
||||
If using the parent portal:
|
||||
- Assign login credentials to family contacts
|
||||
- Parents can view all children in their family
|
||||
- Shared document access for family
|
||||
|
||||
## Migration Instructions
|
||||
|
||||
### For New Installations
|
||||
|
||||
The family field (`fk_soc`) is included automatically in the child table when you install the module.
|
||||
|
||||
### For Existing Installations
|
||||
|
||||
If you installed the module before the family feature was added, run the migration script:
|
||||
|
||||
```sql
|
||||
-- Run this SQL script on your database
|
||||
-- File: sql/llx_childcare_child_add_family.sql
|
||||
|
||||
ALTER TABLE llx_childcare_child ADD COLUMN fk_soc integer DEFAULT NULL AFTER entity;
|
||||
ALTER TABLE llx_childcare_child ADD INDEX idx_childcare_child_fk_soc (fk_soc);
|
||||
ALTER TABLE llx_childcare_child ADD CONSTRAINT fk_childcare_child_soc
|
||||
FOREIGN KEY (fk_soc) REFERENCES llx_societe(rowid);
|
||||
```
|
||||
|
||||
**How to run:**
|
||||
|
||||
1. Backup your database first!
|
||||
2. Access your database via phpMyAdmin, MySQL CLI, or other tool
|
||||
3. Execute the SQL commands from `sql/llx_childcare_child_add_family.sql`
|
||||
4. Verify the column was added: `DESCRIBE llx_childcare_child;`
|
||||
5. Refresh your Dolibarr interface
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### "Family Name dropdown is empty"
|
||||
|
||||
**Cause**: No third parties exist in your database
|
||||
**Solution**: Create at least one third party (family) first
|
||||
|
||||
### "Can't save child with family selected"
|
||||
|
||||
**Cause**: Database migration not run or foreign key constraint issue
|
||||
**Solution**:
|
||||
1. Check if `fk_soc` column exists in `llx_childcare_child` table
|
||||
2. Run migration script if needed
|
||||
3. Verify the selected family exists in `llx_societe` table
|
||||
|
||||
### "Family link disappeared after saving"
|
||||
|
||||
**Cause**: Form submission not including the `socid` parameter
|
||||
**Solution**: Check the form processing logic in your page
|
||||
|
||||
### "How do I unlink a child from a family?"
|
||||
|
||||
**Solution**:
|
||||
1. Edit the child record
|
||||
2. Select the blank option in the Family Name dropdown
|
||||
3. Save
|
||||
|
||||
## Advanced Usage
|
||||
|
||||
### Custom Family Types
|
||||
|
||||
You can configure Dolibarr to use a custom third party type for families:
|
||||
|
||||
1. Go to **Setup → Dictionaries → Third Party Types**
|
||||
2. Add a new type: "Family" with code `family`
|
||||
3. Modify the family selector to filter by this type
|
||||
|
||||
### Family Custom Fields
|
||||
|
||||
Add extra fields to families via Dolibarr's extrafields:
|
||||
|
||||
1. Go to **Setup → Extra Fields**
|
||||
2. Select **Third Parties**
|
||||
3. Add custom fields:
|
||||
- Number of children enrolled
|
||||
- Preferred communication method
|
||||
- Billing cycle preference
|
||||
- Special notes or requirements
|
||||
|
||||
### Integration with Dolibarr Modules
|
||||
|
||||
Families work seamlessly with other Dolibarr features:
|
||||
|
||||
- **Invoicing**: Bill families for childcare services
|
||||
- **Proposals**: Send enrollment proposals to families
|
||||
- **Contracts**: Create service contracts with families
|
||||
- **Contacts**: Manage multiple parents/guardians
|
||||
- **Agenda**: Schedule meetings and events with families
|
||||
- **Documents**: Share documents with family contacts
|
||||
|
||||
## Frequently Asked Questions
|
||||
|
||||
**Q: Do I have to use families?**
|
||||
A: No, the family field is optional. Children can exist without a family link.
|
||||
|
||||
**Q: Can a child belong to multiple families?**
|
||||
A: No, each child can only be linked to one family at a time. For split custody, see [Multiple Families](#multiple-families).
|
||||
|
||||
**Q: What type should I use for family third parties?**
|
||||
A: You can use any type. Common choices:
|
||||
- **Neither customer nor prospect** (type 0) - For families not involved in other business
|
||||
- **Customer** (type 1) - If you invoice them for childcare services
|
||||
- Create a custom "Family" type in dictionaries
|
||||
|
||||
**Q: Can I bill families automatically?**
|
||||
A: Future versions will include automatic invoice generation. For now, manually create invoices linked to the family third party.
|
||||
|
||||
**Q: How do I export family data?**
|
||||
A: Use Dolibarr's export tool:
|
||||
1. **Tools → Export**
|
||||
2. Select **Third Parties** and **Children**
|
||||
3. Include family name fields
|
||||
4. Export to CSV or Excel
|
||||
|
||||
## Related Documentation
|
||||
|
||||
- [User Guide](user-guide.md) - General module usage
|
||||
- [Database Schema](database-schema.md) - Technical field reference
|
||||
- [Development Guide](development.md) - For developers integrating family features
|
||||
- [Dolibarr Third Party Documentation](https://wiki.dolibarr.org/index.php/Third_parties_/_Customers_/_Prospects)
|
||||
|
||||
---
|
||||
|
||||
**Version**: 1.1.0
|
||||
**Last Updated**: March 2026
|
||||
**Module**: MokoDoliCare Childcare Management
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,469 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring the MokoDoliCare Childcare Management Module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 12.0 or higher
|
||||
- **PHP**: Version 7.4 or higher (8.0+ recommended)
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql (database connectivity)
|
||||
- gd or imagick (image processing)
|
||||
- curl (external communications)
|
||||
- json (JSON handling)
|
||||
- xml (XML processing)
|
||||
- mbstring (multi-byte string support)
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### Method 1: Installation from ZIP File (Recommended)
|
||||
|
||||
If you have a ready-to-deploy ZIP file (e.g., `module_childcare-1.0.0.zip`):
|
||||
|
||||
1. **Log in** to Dolibarr as an administrator
|
||||
2. Navigate to **Home → Setup → Modules → Deploy External Module**
|
||||
3. Click **Browse** and select the ZIP file
|
||||
4. Click **Upload**
|
||||
5. Wait for the upload and extraction to complete
|
||||
6. The module will appear in the modules list
|
||||
|
||||
### Method 2: Installation from Git Repository
|
||||
|
||||
For development or latest version:
|
||||
|
||||
```bash
|
||||
# Navigate to Dolibarr's custom directory
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
|
||||
# Clone the repository
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliCare.git childcare
|
||||
|
||||
# Copy module files from src/ directory
|
||||
cp -r childcare/src/* childcare/
|
||||
|
||||
# Set proper permissions
|
||||
chown -R www-data:www-data childcare/
|
||||
find childcare/ -type d -exec chmod 755 {} \;
|
||||
find childcare/ -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### Method 3: Manual Installation from Extracted Files
|
||||
|
||||
```bash
|
||||
# Extract module files to custom directory
|
||||
unzip module_childcare-1.0.0.zip -d /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Set ownership (adjust user:group for your system)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
## Activating the Module
|
||||
|
||||
After installation files are in place:
|
||||
|
||||
1. **Log in** to Dolibarr as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. In the search box, type **"Childcare"**
|
||||
4. Find **"Childcare Management"** in the list
|
||||
5. Click the **Activate** toggle button
|
||||
6. Wait for confirmation: "Module activated successfully"
|
||||
|
||||
### Verify Installation
|
||||
|
||||
After activation, verify the module is working:
|
||||
|
||||
1. **Check Menu**: You should see **"Childcare"** in the top navigation menu
|
||||
2. **Check Tables**: Database tables should be created automatically
|
||||
```sql
|
||||
SHOW TABLES LIKE 'llx_childcare%';
|
||||
```
|
||||
Expected: `llx_childcare_child`, `llx_childcare_attendance`, `llx_childcare_activity`
|
||||
|
||||
3. **Check Module Status**:
|
||||
```sql
|
||||
SELECT value FROM llx_const WHERE name = 'MAIN_MODULE_CHILDCARE';
|
||||
```
|
||||
Expected: `1` (active)
|
||||
|
||||
## Post-Installation Configuration
|
||||
|
||||
### 1. Configure User Permissions
|
||||
|
||||
Set up permissions for your staff:
|
||||
|
||||
1. Go to **Home → Users & Groups → Users**
|
||||
2. Click on a user name
|
||||
3. Go to the **Permissions** tab
|
||||
4. Under **Childcare** section, enable appropriate permissions:
|
||||
- **Read child records** - View child information
|
||||
- **Create/Edit child records** - Add and modify children
|
||||
- **Delete child records** - Remove child records (admins only)
|
||||
- **Read attendance** - View attendance records
|
||||
- **Create/Edit attendance** - Record attendance
|
||||
- **Read activities** - View activities
|
||||
- **Create/Edit activities** - Manage activities
|
||||
5. Click **Save**
|
||||
|
||||
### 2. Module Settings (Optional)
|
||||
|
||||
Configure module options:
|
||||
|
||||
|
||||
1. Navigate to **Home → Setup → Modules → Childcare Management → Setup**
|
||||
2. Configure options as needed (configuration interface may be minimal in v1.0.0)
|
||||
3. Save changes
|
||||
|
||||
### 3. Test Functionality
|
||||
|
||||
Verify the module works correctly:
|
||||
|
||||
1. **Create a Test Child**:
|
||||
- Go to **Childcare → Children → New Child**
|
||||
- Fill in required fields (First Name, Last Name, Date of Birth)
|
||||
- Click **Create**
|
||||
- Verify child appears in list
|
||||
|
||||
2. **Record Test Attendance**:
|
||||
- Go to **Childcare → Attendance → New Record**
|
||||
- Select the test child
|
||||
- Enter today's date and check-in time
|
||||
- Click **Save**
|
||||
- Verify record appears
|
||||
|
||||
3. **Create Test Activity**:
|
||||
- Go to **Childcare → Activities → New Activity**
|
||||
- Fill in Label, Date
|
||||
- Click **Create**
|
||||
- Verify activity appears in schedule
|
||||
|
||||
## Database Setup
|
||||
|
||||
### Automatic Setup (Default)
|
||||
|
||||
The module automatically creates database tables when activated. Tables created:
|
||||
|
||||
- `llx_childcare_child` - Child records
|
||||
- `llx_childcare_attendance` - Attendance tracking
|
||||
- `llx_childcare_activity` - Activity management
|
||||
|
||||
### Manual Setup (If Automatic Fails)
|
||||
|
||||
If tables aren't created automatically:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/childcare/sql/
|
||||
|
||||
# Create tables
|
||||
mysql -u username -p database_name < llx_childcare_child.sql
|
||||
mysql -u username -p database_name < llx_childcare_attendance.sql
|
||||
mysql -u username -p database_name < llx_childcare_activity.sql
|
||||
|
||||
# Create indexes and foreign keys
|
||||
mysql -u username -p database_name < llx_childcare_child.key.sql
|
||||
mysql -u username -p database_name < llx_childcare_attendance.key.sql
|
||||
mysql -u username -p database_name < llx_childcare_activity.key.sql
|
||||
```
|
||||
|
||||
### Verify Database Setup
|
||||
|
||||
```sql
|
||||
-- Check tables exist
|
||||
SHOW TABLES LIKE 'llx_childcare%';
|
||||
|
||||
-- Check table structure
|
||||
DESCRIBE llx_childcare_child;
|
||||
DESCRIBE llx_childcare_attendance;
|
||||
DESCRIBE llx_childcare_activity;
|
||||
|
||||
-- Verify foreign keys
|
||||
SELECT CONSTRAINT_NAME, TABLE_NAME, REFERENCED_TABLE_NAME
|
||||
FROM information_schema.KEY_COLUMN_USAGE
|
||||
WHERE TABLE_SCHEMA = 'your_database_name'
|
||||
AND TABLE_NAME LIKE 'llx_childcare%'
|
||||
AND REFERENCED_TABLE_NAME IS NOT NULL;
|
||||
```
|
||||
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
**Problem**: Can't find "Childcare Management" in module list
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Clear Cache**:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/documents/install.lock
|
||||
```
|
||||
Then refresh browser (Ctrl+Shift+R)
|
||||
|
||||
2. **Check File Location**:
|
||||
```bash
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/core/modules/modMokoDoliCare.class.php
|
||||
```
|
||||
File must exist
|
||||
|
||||
3. **Check Permissions**:
|
||||
```bash
|
||||
# Files should be readable by web server
|
||||
chmod 644 /path/to/dolibarr/htdocs/custom/childcare/core/modules/modMokoDoliCare.class.php
|
||||
```
|
||||
|
||||
4. **Check PHP Syntax**:
|
||||
```bash
|
||||
php -l /path/to/dolibarr/htdocs/custom/childcare/core/modules/modMokoDoliCare.class.php
|
||||
```
|
||||
Should show "No syntax errors"
|
||||
|
||||
### Permission Errors
|
||||
|
||||
**Problem**: "Access Forbidden" or can't access files
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Fix File Ownership**:
|
||||
```bash
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
```
|
||||
|
||||
2. **Fix File Permissions**:
|
||||
```bash
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type d -exec chmod 755 {} \;
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
3. **Check SELinux** (if applicable):
|
||||
```bash
|
||||
# Temporarily disable to test
|
||||
setenforce 0
|
||||
```
|
||||
|
||||
### Database Errors
|
||||
|
||||
**Problem**: Tables not created or database errors
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Check Database User Permissions**:
|
||||
```sql
|
||||
SHOW GRANTS FOR 'dolibarr_user'@'localhost';
|
||||
```
|
||||
User needs: SELECT, INSERT, UPDATE, DELETE, CREATE, ALTER, INDEX, DROP
|
||||
|
||||
2. **Manually Create Tables**: See [Manual Setup](#manual-setup-if-automatic-fails) above
|
||||
|
||||
3. **Check Database Connection**:
|
||||
```bash
|
||||
mysql -u dolibarr_user -p dolibarr_db -e "SELECT 1;"
|
||||
```
|
||||
|
||||
### Module Activates But Doesn't Work
|
||||
|
||||
**Problem**: Module active but menu doesn't appear or features don't work
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Check User Permissions**:
|
||||
- User must have at least "Read" permission
|
||||
- Go to **Users & Groups → [User] → Permissions**
|
||||
- Enable Childcare permissions
|
||||
|
||||
2. **Clear All Caches**:
|
||||
```bash
|
||||
# Server cache
|
||||
rm -rf /path/to/dolibarr/documents/install.lock
|
||||
|
||||
# Browser cache
|
||||
# Press Ctrl+Shift+Del and clear cache
|
||||
```
|
||||
|
||||
3. **Check Error Logs**:
|
||||
```bash
|
||||
tail -f /var/log/apache2/error.log
|
||||
# or
|
||||
tail -f /var/log/nginx/error.log
|
||||
# and
|
||||
tail -f /path/to/dolibarr/documents/dolibarr.log
|
||||
```
|
||||
|
||||
## Advanced Configuration
|
||||
|
||||
### Multi-Entity Setup
|
||||
|
||||
For managing multiple childcare facilities:
|
||||
|
||||
1. **Enable Multi-Entity** in Dolibarr:
|
||||
- Home → Setup → Other Setup → Multi-entity
|
||||
- Enable multi-entity mode
|
||||
|
||||
2. **Create Entities**:
|
||||
- Home → Setup → Entities → New Entity
|
||||
- Create entity for each facility
|
||||
|
||||
3. **Assign Users to Entities**:
|
||||
- Home → Users & Groups → [User] → Entity tab
|
||||
- Select appropriate entities
|
||||
|
||||
4. **Data Separation**: Each entity will have separate children, attendance, and activities
|
||||
|
||||
### Custom Configuration Constants
|
||||
|
||||
Add custom configuration:
|
||||
|
||||
```sql
|
||||
-- Example: Set default child status
|
||||
INSERT INTO llx_const (name, value, type, note, entity)
|
||||
VALUES ('CHILDCARE_DEFAULT_STATUS', '1', 'chaine', 'Default child status (1=Active)', 1);
|
||||
|
||||
-- Example: Enable auto-reference generation
|
||||
INSERT INTO llx_const (name, value, type, note, entity)
|
||||
VALUES ('CHILDCARE_AUTO_REF', '1', 'chaine', 'Auto-generate references', 1);
|
||||
```
|
||||
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
### Step 1: Deactivate Module
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find "Childcare Management" and click **Deactivate**
|
||||
3. Confirm deactivation
|
||||
|
||||
### Step 2: Remove Files (Optional)
|
||||
|
||||
```bash
|
||||
# Backup first!
|
||||
tar -czf childcare_backup.tar.gz /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Remove module directory
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/childcare/
|
||||
```
|
||||
|
||||
### Step 3: Remove Database Tables (Optional)
|
||||
|
||||
**Warning**: This permanently deletes all childcare data!
|
||||
|
||||
```bash
|
||||
# Backup database first!
|
||||
mysqldump -u user -p database_name \
|
||||
llx_childcare_child \
|
||||
llx_childcare_attendance \
|
||||
llx_childcare_activity > childcare_backup.sql
|
||||
|
||||
# Then drop tables
|
||||
mysql -u user -p database_name << EOF
|
||||
DROP TABLE IF EXISTS llx_childcare_attendance;
|
||||
DROP TABLE IF EXISTS llx_childcare_activity;
|
||||
DROP TABLE IF EXISTS llx_childcare_child;
|
||||
EOF
|
||||
```
|
||||
|
||||
### Step 4: Remove Configuration (Optional)
|
||||
|
||||
```sql
|
||||
-- Remove module constants
|
||||
DELETE FROM llx_const WHERE name LIKE '%CHILDCARE%';
|
||||
|
||||
-- Remove module permissions
|
||||
DELETE FROM llx_user_rights WHERE fk_id >= 60000101 AND fk_id <= 60000107;
|
||||
```
|
||||
|
||||
## Upgrading
|
||||
|
||||
### From Version X.X to Version Y.Y
|
||||
|
||||
1. **Backup Everything**:
|
||||
```bash
|
||||
# Backup files
|
||||
tar -czf childcare_files_backup.tar.gz /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Backup database
|
||||
mysqldump -u user -p database llx_childcare_child llx_childcare_attendance llx_childcare_activity > backup.sql
|
||||
```
|
||||
|
||||
2. **Deactivate Module**:
|
||||
- Home → Setup → Modules → Childcare → Deactivate
|
||||
|
||||
3. **Update Files**:
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/childcare/
|
||||
git pull origin main
|
||||
# or extract new version ZIP
|
||||
```
|
||||
|
||||
4. **Reactivate Module**:
|
||||
- Home → Setup → Modules → Childcare → Activate
|
||||
- Database migrations run automatically
|
||||
|
||||
5. **Verify**:
|
||||
- Test key functionality
|
||||
- Check for errors in logs
|
||||
- Verify data integrity
|
||||
|
||||
## System Requirements Check
|
||||
|
||||
Run this checklist before installation:
|
||||
|
||||
```bash
|
||||
# PHP version (should be 7.4+)
|
||||
php -v
|
||||
|
||||
# Required PHP extensions
|
||||
php -m | grep -E "mysqli|pdo|gd|curl|json|xml|mbstring"
|
||||
|
||||
# Database connectivity
|
||||
mysql -u dolibarr_user -p -e "SELECT VERSION();"
|
||||
|
||||
# Disk space (need at least 100MB free)
|
||||
df -h /path/to/dolibarr/
|
||||
|
||||
# Directory writable
|
||||
touch /path/to/dolibarr/htdocs/custom/test && rm /path/to/dolibarr/htdocs/custom/test && echo "Writable" || echo "Not writable"
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
After successful installation:
|
||||
|
||||
1. ⚡ **Quick Start**: Follow the [Quick Start Guide](quick-start.md) for 10-minute setup
|
||||
2. 📖 **Learn Features**: Read the [User Guide](user-guide.md) for complete documentation
|
||||
3. 🔧 **Configure**: See [Admin Guide](admin-guide.md) for advanced configuration
|
||||
4. 👥 **Set Up Users**: Configure permissions for all staff members
|
||||
5. 📝 **Add Data**: Start adding children, recording attendance, and scheduling activities
|
||||
|
||||
## Need Help?
|
||||
|
||||
- 📖 **Documentation**: [docs/README.md](README.md)
|
||||
- 🛠️ **Troubleshooting**: [troubleshooting.md](troubleshooting.md)
|
||||
- 🐛 **Report Issues**: [GitHub Issues](https://github.com/mokoconsulting-tech/MokoDoliCare/issues)
|
||||
- 💬 **Community**: [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
- 🏢 **Professional Support**: [Moko Consulting](https://mokoconsulting.tech)
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: 2026-02-19
|
||||
**Version**: 1.0.0
|
||||
**For**: MokoDoliCare Childcare Management Module
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,402 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Quick Start Guide
|
||||
|
||||
Get up and running with MokoDoliCare in 10 minutes. This guide walks you through the essential steps to start managing your childcare facility.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before you begin, ensure:
|
||||
- ✅ Dolibarr 12.0+ is installed and running
|
||||
- ✅ You have administrator access to Dolibarr
|
||||
- ✅ The MokoDoliCare module is installed (see [Installation Guide](installation.md))
|
||||
|
||||
## Step 1: Activate the Module (2 minutes)
|
||||
|
||||
1. **Log in** to Dolibarr as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. In the search box, type "Childcare"
|
||||
4. Find **"Childcare Management"** in the list
|
||||
5. Click the **toggle/activate button** next to it
|
||||
6. Wait for confirmation message: "Module activated successfully"
|
||||
|
||||
✅ **Success Check**: You should now see "Childcare" in the top navigation menu.
|
||||
|
||||
---
|
||||
|
||||
## Step 2: Configure Permissions (3 minutes)
|
||||
|
||||
Set up user permissions for your staff.
|
||||
|
||||
### For Administrators
|
||||
|
||||
1. Go to **Home → Users & Groups → Users**
|
||||
2. Click on a user name
|
||||
3. Go to the **Permissions** tab
|
||||
4. Under **Childcare** section, enable:
|
||||
- ✅ **Read child records**
|
||||
- ✅ **Create/Edit child records**
|
||||
- ✅ **Delete child records**
|
||||
- ✅ **Read attendance**
|
||||
- ✅ **Create/Edit attendance**
|
||||
- ✅ **Read activities**
|
||||
- ✅ **Create/Edit activities**
|
||||
5. Click **Save**
|
||||
|
||||
### For Regular Staff
|
||||
|
||||
Enable only necessary permissions:
|
||||
- ✅ Read child records
|
||||
- ✅ Read/Create attendance
|
||||
- ✅ Read activities
|
||||
|
||||
### Permission Quick Reference
|
||||
|
||||
| Role | Child Records | Attendance | Activities |
|
||||
|------|---------------|------------|------------|
|
||||
| **Administrator** | Read/Write/Delete | Read/Write | Read/Write |
|
||||
| **Lead Teacher** | Read/Write | Read/Write | Read/Write |
|
||||
| **Teacher** | Read | Read/Write | Read |
|
||||
| **Office Staff** | Read/Write | Read | Read |
|
||||
|
||||
---
|
||||
|
||||
## Step 3: Add Your First Child (2 minutes)
|
||||
|
||||
Let's create a child record.
|
||||
|
||||
1. Click **Childcare** in the top menu
|
||||
2. Select **Children → New Child**
|
||||
3. Fill in the required fields:
|
||||
|
||||
**Basic Information:**
|
||||
- **Reference**: `CHILD001` (auto-generated if left blank)
|
||||
- **First Name**: `Emma`
|
||||
- **Last Name**: `Johnson`
|
||||
- **Date of Birth**: `2020-03-15` (use date picker)
|
||||
- **Gender**: `Female`
|
||||
|
||||
**Important Information:**
|
||||
- **Allergies**: `Peanut allergy (severe - EpiPen required)`
|
||||
- **Medical Notes**: `Asthma - uses inhaler as needed`
|
||||
- **Emergency Contact**: `Sarah Johnson (Mother) - (555) 123-4567`
|
||||
- **Enrollment Date**: `2023-09-01`
|
||||
|
||||
**Status:**
|
||||
- **Status**: `Active` (checked)
|
||||
|
||||
4. Click **Create**
|
||||
|
||||
✅ **Success Check**: You should see the child's card page with all entered information.
|
||||
|
||||
### Quick Tips for Child Records
|
||||
|
||||
- 📝 **Reference numbers** help identify children quickly. Use a consistent format like `CHILD001`, `CHILD002`, etc.
|
||||
- 🚨 **Emergency contacts** are critical. Always include phone numbers and relationships.
|
||||
- 💊 **Allergies and medical notes** should be detailed and specific.
|
||||
- 📅 **Date of Birth** is used to calculate age automatically.
|
||||
|
||||
---
|
||||
|
||||
## Step 4: Record Attendance (2 minutes)
|
||||
|
||||
Track when children check in and out.
|
||||
|
||||
1. From the top menu: **Childcare → Attendance**
|
||||
2. Click **New Attendance Record**
|
||||
3. Fill in the form:
|
||||
- **Child**: Select `Emma Johnson` from dropdown
|
||||
- **Date**: Today's date (default)
|
||||
- **Check-in Time**: `08:30 AM`
|
||||
- **Check-out Time**: `03:30 PM` (can be left blank if child is still present)
|
||||
- **Status**: `Present`
|
||||
- **Notes**: `Had a great day. Ate all lunch. Participated in painting activity.`
|
||||
4. Click **Save**
|
||||
|
||||
✅ **Success Check**: The attendance record appears in the list.
|
||||
|
||||
### Attendance Recording Tips
|
||||
|
||||
- ⏰ **Check-in time** can be recorded immediately when child arrives
|
||||
- ⏰ **Check-out time** can be added later when child is picked up
|
||||
- 📝 **Daily notes** help parents stay informed about their child's day
|
||||
- 📊 **Status** options: Present (1), Absent (0), Partial attendance (2)
|
||||
|
||||
### Quick Attendance Workflow
|
||||
|
||||
```
|
||||
Morning:
|
||||
1. Child arrives → Record check-in time
|
||||
2. Add any morning notes (mood, items brought, etc.)
|
||||
|
||||
Afternoon:
|
||||
3. Throughout day → Update notes (meals, activities, behavior)
|
||||
4. Child departs → Record check-out time
|
||||
5. Add final notes for parents
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Step 5: Schedule an Activity (1 minute)
|
||||
|
||||
Plan activities for your children.
|
||||
|
||||
1. Go to **Childcare → Activities**
|
||||
2. Click **New Activity**
|
||||
3. Complete the form:
|
||||
- **Reference**: `ACT-2026-02-19-001` (or auto-generate)
|
||||
- **Label**: `Morning Circle Time`
|
||||
- **Description**: `Group circle time with songs, weather, and calendar`
|
||||
- **Date**: Today's date
|
||||
- **Time**: `09:00 AM`
|
||||
- **Activity Type**: `Learning`
|
||||
- **Status**: `Scheduled`
|
||||
4. Click **Create**
|
||||
|
||||
✅ **Success Check**: Activity appears in today's schedule.
|
||||
|
||||
### Activity Types Reference
|
||||
|
||||
| Type | Use For | Examples |
|
||||
|------|---------|----------|
|
||||
| **Learning** | Educational activities | ABC, numbers, shapes, colors |
|
||||
| **Play** | Free or structured play | Toys, games, building blocks |
|
||||
| **Outdoor** | Outside time | Playground, nature walk, sports |
|
||||
| **Meals** | Eating times | Breakfast, lunch, snacks |
|
||||
| **Naps** | Rest time | Afternoon nap, quiet time |
|
||||
| **Arts** | Creative activities | Painting, drawing, crafts |
|
||||
| **Music** | Musical activities | Singing, instruments, dancing |
|
||||
| **Story Time** | Reading | Books, storytelling circle |
|
||||
|
||||
---
|
||||
|
||||
## Common Daily Workflows
|
||||
|
||||
### Morning Routine
|
||||
|
||||
```
|
||||
1. Review today's attendance list
|
||||
2. Record check-ins as children arrive
|
||||
3. Check activity schedule for the day
|
||||
4. Update any last-minute schedule changes
|
||||
```
|
||||
|
||||
### During the Day
|
||||
|
||||
```
|
||||
1. Update attendance notes throughout the day
|
||||
2. Mark activities as completed
|
||||
3. Document any incidents or special observations
|
||||
4. Take photos (future feature - manual for now)
|
||||
```
|
||||
|
||||
### End of Day
|
||||
|
||||
```
|
||||
1. Record all check-out times
|
||||
2. Complete daily notes for each child
|
||||
3. Review tomorrow's activity schedule
|
||||
4. Prepare any parent communications needed
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Quick Navigation Guide
|
||||
|
||||
### Top Menu Structure
|
||||
|
||||
```
|
||||
Childcare
|
||||
├── Dashboard (overview and statistics)
|
||||
├── Children
|
||||
│ ├── List (view all children)
|
||||
│ └── New Child (add new record)
|
||||
├── Attendance
|
||||
│ ├── Today's Attendance
|
||||
│ ├── Attendance History
|
||||
│ └── New Attendance Record
|
||||
└── Activities
|
||||
├── Activity Schedule
|
||||
└── New Activity
|
||||
```
|
||||
|
||||
### Keyboard Shortcuts
|
||||
|
||||
- `Alt+N` - Quick new record (when on list page)
|
||||
- `Alt+S` - Save current form
|
||||
- `Alt+C` - Cancel and return to list
|
||||
- `Esc` - Close current dialog
|
||||
|
||||
---
|
||||
|
||||
## Sample Data Scenarios
|
||||
|
||||
### Scenario 1: Part-Time Child
|
||||
|
||||
For a child who only attends certain days:
|
||||
|
||||
1. Create child record with enrollment date
|
||||
2. Only record attendance on days they attend
|
||||
3. Leave check-out time blank if they're still present
|
||||
4. Use Status = "Partial" for half-days
|
||||
|
||||
### Scenario 2: Child With Allergies
|
||||
|
||||
Critical information to document:
|
||||
|
||||
1. **Allergies field**: List all allergies with severity
|
||||
2. **Medical Notes**: Include emergency procedures
|
||||
3. **Emergency Contact**: Ensure parent contact is accurate
|
||||
4. **Public Notes**: Add reminder visible to all staff: "CHECK ALLERGY LIST"
|
||||
|
||||
### Scenario 3: Daily Activity Planning
|
||||
|
||||
Planning a full day of activities:
|
||||
|
||||
```
|
||||
09:00 - Morning Circle (Learning)
|
||||
09:30 - Free Play (Play)
|
||||
10:00 - Snack Time (Meals)
|
||||
10:30 - Outdoor Play (Outdoor)
|
||||
11:30 - Art Project (Arts)
|
||||
12:00 - Lunch (Meals)
|
||||
12:30 - Nap Time (Naps)
|
||||
14:30 - Story Time (Story Time)
|
||||
15:00 - Music and Movement (Music)
|
||||
15:30 - Pick-up time
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting Quick Fixes
|
||||
|
||||
### Can't See Childcare Menu
|
||||
|
||||
**Problem**: Childcare doesn't appear in top menu
|
||||
**Solution**:
|
||||
1. Check module is activated (Home → Setup → Modules)
|
||||
2. Verify you have at least "Read" permission
|
||||
3. Refresh your browser (Ctrl+F5)
|
||||
|
||||
### Can't Create New Records
|
||||
|
||||
**Problem**: "Create" button is grayed out or missing
|
||||
**Solution**:
|
||||
1. Check your permissions (need "Write" permission)
|
||||
2. Ensure you're logged in as correct user
|
||||
3. Contact administrator to grant permissions
|
||||
|
||||
### Child Not Appearing in Attendance Dropdown
|
||||
|
||||
**Problem**: Can't find child when recording attendance
|
||||
**Solution**:
|
||||
1. Verify child status is "Active"
|
||||
2. Check child record was saved properly
|
||||
3. Refresh the page
|
||||
4. Verify you're in the correct entity (multi-entity installations)
|
||||
|
||||
### Times Not Saving Correctly
|
||||
|
||||
**Problem**: Check-in/out times showing wrong time
|
||||
**Solution**:
|
||||
1. Check Dolibarr server timezone settings
|
||||
2. Use 24-hour format (HH:MM)
|
||||
3. Ensure time is in valid format
|
||||
4. Check browser timezone matches server
|
||||
|
||||
---
|
||||
|
||||
## Next Steps
|
||||
|
||||
Now that you're up and running, explore these features:
|
||||
|
||||
### Week 1 Goals
|
||||
- [ ] Add all currently enrolled children
|
||||
- [ ] Set up user permissions for all staff
|
||||
- [ ] Record attendance for 3 consecutive days
|
||||
- [ ] Create a week's worth of activity schedules
|
||||
|
||||
### Week 2 Goals
|
||||
- [ ] Review attendance reports
|
||||
- [ ] Update any missing medical information
|
||||
- [ ] Establish daily workflow patterns
|
||||
- [ ] Train all staff on the system
|
||||
|
||||
### Month 1 Goals
|
||||
- [ ] Generate first monthly reports
|
||||
- [ ] Fine-tune activity types for your facility
|
||||
- [ ] Establish backup procedures
|
||||
- [ ] Gather feedback from staff
|
||||
|
||||
---
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Documentation Resources
|
||||
|
||||
- 📖 [User Guide](user-guide.md) - Detailed feature documentation
|
||||
- 🔧 [Admin Guide](admin-guide.md) - System configuration and management
|
||||
- 💾 [Database Schema](database-schema.md) - Technical database details
|
||||
- 🛠️ [Troubleshooting](troubleshooting.md) - Common issues and solutions
|
||||
|
||||
### Support Channels
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: Community support for general questions
|
||||
- **Documentation**: Check this guide and other docs first
|
||||
|
||||
### Training Resources
|
||||
|
||||
- Watch video tutorials (coming soon)
|
||||
- Download user manual PDF (coming soon)
|
||||
- Schedule training session with administrator
|
||||
|
||||
---
|
||||
|
||||
## Quick Reference Card
|
||||
|
||||
Print this for your desk:
|
||||
|
||||
```
|
||||
╔══════════════════════════════════════════════════════════╗
|
||||
║ MokoDoliCare Quick Reference ║
|
||||
╠══════════════════════════════════════════════════════════╣
|
||||
║ NEW CHILD: Childcare → Children → New Child ║
|
||||
║ ATTENDANCE: Childcare → Attendance → New Record ║
|
||||
║ ACTIVITY: Childcare → Activities → New Activity ║
|
||||
║ ║
|
||||
║ REQUIRED FIELDS: ║
|
||||
║ • Child: First/Last Name, Date of Birth ║
|
||||
║ • Attendance: Child, Date ║
|
||||
║ • Activity: Label, Date ║
|
||||
║ ║
|
||||
║ EMERGENCY INFO: ║
|
||||
║ Always include: Contact Name, Phone, Relationship ║
|
||||
║ ║
|
||||
║ DAILY CHECKLIST: ║
|
||||
║ ☐ Record morning check-ins ║
|
||||
║ ☐ Update daily notes ║
|
||||
║ ☐ Record check-outs ║
|
||||
║ ☐ Review tomorrow's schedule ║
|
||||
╚══════════════════════════════════════════════════════════╝
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
**Congratulations!** 🎉 You're now ready to use MokoDoliCare to manage your childcare facility efficiently.
|
||||
|
||||
**Next**: Read the [User Guide](user-guide.md) for complete feature documentation.
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: 2026-02-19
|
||||
**Version**: 1.0.0
|
||||
**Estimated Time**: 10 minutes
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,316 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Remote Check-In and Payroll Time Clock Feature
|
||||
|
||||
## Overview
|
||||
|
||||
The Remote Check-In feature enables parents/guardians to independently sign their children in and out using a tablet interface at the childcare facility. This eliminates the need for staff to manually record every check-in/check-out, streamlining the attendance process while maintaining accurate records with digital signatures.
|
||||
|
||||
## Key Features
|
||||
|
||||
### 1. Parent/Guardian Authentication
|
||||
- Each parent/guardian has a unique username and PIN (4-6 digits)
|
||||
- PIN is securely hashed using PHP's password_hash() function
|
||||
- Multiple parents can be associated with a single child
|
||||
- Primary contact designation
|
||||
|
||||
### 2. Tablet Check-In Interface
|
||||
- Full-screen, tablet-optimized interface
|
||||
- Simple 3-step process:
|
||||
1. Parent enters username and PIN
|
||||
2. Parent selects Check-In or Check-Out
|
||||
3. Parent signs on touchscreen
|
||||
- Beautiful gradient design optimized for tablets
|
||||
- Touch-friendly buttons and signature pad
|
||||
|
||||
### 3. Digital Signature Capture
|
||||
- Canvas-based signature pad
|
||||
- Touch and mouse support
|
||||
- Signatures stored as base64-encoded images
|
||||
- Separate signatures for check-in and check-out
|
||||
|
||||
### 4. Attendance Tracking
|
||||
- Automatic timestamp recording
|
||||
- Links attendance to specific parent who performed the action
|
||||
- Stores digital signatures with each transaction
|
||||
- Prevents duplicate check-ins/check-outs
|
||||
|
||||
### 5. Payroll Time Clock
|
||||
- Accurate time tracking with check-in/check-out timestamps
|
||||
- Parent accountability through signature requirements
|
||||
- Audit trail showing which parent performed each action
|
||||
- Can be used to calculate hours for billing purposes
|
||||
|
||||
## Database Schema
|
||||
|
||||
### New Table: llx_childcare_parent
|
||||
|
||||
Stores parent/guardian information and credentials:
|
||||
|
||||
| Field | Type | Description |
|
||||
|-------|------|-------------|
|
||||
| rowid | integer | Primary key |
|
||||
| entity | integer | Multi-entity support |
|
||||
| fk_child | integer | Foreign key to child |
|
||||
| firstname | varchar(128) | Parent's first name |
|
||||
| lastname | varchar(128) | Parent's last name |
|
||||
| email | varchar(255) | Contact email |
|
||||
| phone | varchar(50) | Contact phone |
|
||||
| relationship | varchar(50) | Relationship to child |
|
||||
| username | varchar(50) | Unique username for check-in |
|
||||
| pin_hash | varchar(255) | Hashed PIN |
|
||||
| is_primary | integer | Primary contact flag |
|
||||
| status | integer | Active/Inactive status |
|
||||
|
||||
### Updated Table: llx_childcare_attendance
|
||||
|
||||
Added fields for remote check-in:
|
||||
|
||||
| Field | Type | Description |
|
||||
|-------|------|-------------|
|
||||
| fk_parent_checkin | integer | Parent who checked in |
|
||||
| fk_parent_checkout | integer | Parent who checked out |
|
||||
| signature_checkin | text | Check-in signature (base64) |
|
||||
| signature_checkout | text | Check-out signature (base64) |
|
||||
|
||||
## Setup Instructions
|
||||
|
||||
### 1. Enable the Module
|
||||
|
||||
After updating the module, Dolibarr will automatically create the new database tables when you enable the module.
|
||||
|
||||
### 2. Add Parent/Guardian Accounts
|
||||
|
||||
1. Navigate to **Childcare → Parents → New Parent**
|
||||
2. Fill in parent information:
|
||||
- First Name and Last Name
|
||||
- Relationship to child
|
||||
- Contact information (email, phone)
|
||||
- Username (used for tablet login)
|
||||
- PIN (4-6 digits)
|
||||
3. Optionally mark as primary contact
|
||||
4. Save the parent record
|
||||
|
||||
### 3. Set Up Tablet Device
|
||||
|
||||
1. Open a web browser on the tablet
|
||||
2. Navigate to: `https://your-dolibarr-url/custom/childcare/tablet_checkin.php`
|
||||
3. Bookmark this page or add it to the home screen
|
||||
4. Set the tablet to prevent sleep/lock
|
||||
5. Consider setting up a kiosk mode browser for security
|
||||
|
||||
### 4. Configure Permissions
|
||||
|
||||
The tablet check-in interface is publicly accessible (no Dolibarr login required) to allow parents to use it independently. However, you should:
|
||||
|
||||
1. Set appropriate network restrictions (e.g., restrict to facility WiFi)
|
||||
2. Use HTTPS for secure communication
|
||||
3. Place tablet in supervised location
|
||||
|
||||
### 5. Staff Access
|
||||
|
||||
Staff with appropriate permissions can:
|
||||
- View attendance records with parent information
|
||||
- Manage parent accounts
|
||||
- View digital signatures
|
||||
- Generate reports
|
||||
|
||||
## Usage Guide
|
||||
|
||||
### For Parents
|
||||
|
||||
1. **Start Check-In**
|
||||
- Approach the tablet at the check-in station
|
||||
- Enter your username
|
||||
- Enter your 4-6 digit PIN
|
||||
- Tap Continue
|
||||
|
||||
2. **Select Action**
|
||||
- Your name and child's name will be displayed
|
||||
- Tap "Check In" or "Check Out"
|
||||
|
||||
3. **Sign**
|
||||
- Sign on the signature pad using your finger or stylus
|
||||
- Tap "Clear Signature" if you need to redo it
|
||||
- Tap "Confirm Check-In" or "Confirm Check-Out"
|
||||
|
||||
4. **Done**
|
||||
- You'll see a success message
|
||||
- Tap "Done" to return to the login screen
|
||||
|
||||
### For Staff
|
||||
|
||||
#### Managing Parents
|
||||
|
||||
1. Navigate to **Childcare → Parents**
|
||||
2. View list of all parents/guardians
|
||||
3. Click "New Parent" to add a new parent
|
||||
4. Click on a parent to view/edit details
|
||||
|
||||
#### Viewing Attendance with Parent Info
|
||||
|
||||
1. Navigate to **Childcare → Attendance**
|
||||
2. Attendance records now show:
|
||||
- Which parent performed check-in
|
||||
- Which parent performed check-out
|
||||
- Digital signatures
|
||||
- Timestamps
|
||||
|
||||
#### Accessing Tablet Interface
|
||||
|
||||
1. Navigate to **Childcare → Tablet Check-In**
|
||||
2. Opens in a new tab optimized for tablets
|
||||
|
||||
## Security Considerations
|
||||
|
||||
### PIN Security
|
||||
|
||||
- PINs are hashed using `password_hash()` with bcrypt
|
||||
- Never stored in plain text
|
||||
- Cannot be retrieved, only reset
|
||||
|
||||
### Network Security
|
||||
|
||||
Recommendations:
|
||||
1. Use HTTPS for all connections
|
||||
2. Restrict tablet to facility WiFi network
|
||||
3. Set up IP whitelisting if possible
|
||||
4. Use tablet in supervised area
|
||||
|
||||
### Session Security
|
||||
|
||||
- Sessions expire after successful check-in/check-out
|
||||
- No persistent login on tablet
|
||||
- Each transaction requires re-authentication
|
||||
|
||||
### Data Privacy
|
||||
|
||||
- Signatures are stored securely in the database
|
||||
- Access controlled by Dolibarr permissions
|
||||
- Complies with childcare record-keeping requirements
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### "Invalid username or PIN"
|
||||
|
||||
- Verify parent account is active
|
||||
- Check username is entered correctly (case-sensitive)
|
||||
- Verify PIN is 4-6 digits
|
||||
- Ensure parent is associated with an active child
|
||||
|
||||
### Signature Not Working
|
||||
|
||||
- Try using a different browser (Chrome or Safari recommended)
|
||||
- Check touch screen calibration
|
||||
- Try using a stylus instead of finger
|
||||
- Clear browser cache
|
||||
|
||||
### "Session expired"
|
||||
|
||||
- Start over from the beginning
|
||||
- This is a security feature to prevent unauthorized use
|
||||
- Re-authenticate with username and PIN
|
||||
|
||||
### Database Errors
|
||||
|
||||
If you see database errors after upgrading:
|
||||
1. Disable the module
|
||||
2. Re-enable the module to run SQL updates
|
||||
3. Check database logs for specific errors
|
||||
4. Verify database user has CREATE TABLE permissions
|
||||
|
||||
## Payroll Time Clock Usage
|
||||
|
||||
### Calculate Hours
|
||||
|
||||
The attendance records can be used for payroll calculations:
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
c.firstname, c.lastname,
|
||||
a.attendance_date,
|
||||
a.check_in_time,
|
||||
a.check_out_time,
|
||||
TIMEDIFF(a.check_out_time, a.check_in_time) as hours_attended,
|
||||
p1.firstname as checkin_parent,
|
||||
p2.firstname as checkout_parent
|
||||
FROM llx_childcare_attendance a
|
||||
INNER JOIN llx_childcare_child c ON a.fk_child = c.rowid
|
||||
LEFT JOIN llx_childcare_parent p1 ON a.fk_parent_checkin = p1.rowid
|
||||
LEFT JOIN llx_childcare_parent p2 ON a.fk_parent_checkout = p2.rowid
|
||||
WHERE a.attendance_date BETWEEN '2026-03-01' AND '2026-03-31'
|
||||
ORDER BY c.lastname, a.attendance_date;
|
||||
```
|
||||
|
||||
### Export for Payroll
|
||||
|
||||
You can export attendance data including:
|
||||
- Child name
|
||||
- Date and time stamps
|
||||
- Total hours
|
||||
- Parent signatures (for verification)
|
||||
|
||||
### Billing Integration
|
||||
|
||||
Use the attendance data to:
|
||||
- Calculate hourly billing
|
||||
- Generate monthly invoices
|
||||
- Track overtime hours
|
||||
- Provide detailed statements to parents
|
||||
|
||||
## Future Enhancements
|
||||
|
||||
Potential improvements for future versions:
|
||||
|
||||
1. **Photo Verification**: Capture photo during check-in/check-out
|
||||
2. **QR Code Login**: Alternative to username/PIN
|
||||
3. **Biometric Authentication**: Fingerprint or face recognition
|
||||
4. **SMS Notifications**: Alert parents on check-in/check-out
|
||||
5. **Mobile App**: Dedicated mobile application
|
||||
6. **Reports Dashboard**: Real-time attendance dashboard
|
||||
7. **Bulk Operations**: Check in/out multiple children at once
|
||||
8. **Schedule Integration**: Compare attendance to scheduled times
|
||||
9. **Late Pickup Alerts**: Automatic notifications for late pickups
|
||||
10. **Attendance Analytics**: Patterns and statistics
|
||||
|
||||
## API Integration
|
||||
|
||||
For custom integrations, you can query the attendance data:
|
||||
|
||||
```php
|
||||
// Get today's attendance
|
||||
$sql = "SELECT a.*, c.firstname, c.lastname,
|
||||
p1.firstname as checkin_parent_name,
|
||||
p2.firstname as checkout_parent_name
|
||||
FROM ".MAIN_DB_PREFIX."childcare_attendance a
|
||||
INNER JOIN ".MAIN_DB_PREFIX."childcare_child c ON a.fk_child = c.rowid
|
||||
LEFT JOIN ".MAIN_DB_PREFIX."childcare_parent p1 ON a.fk_parent_checkin = p1.rowid
|
||||
LEFT JOIN ".MAIN_DB_PREFIX."childcare_parent p2 ON a.fk_parent_checkout = p2.rowid
|
||||
WHERE a.attendance_date = CURDATE()";
|
||||
```
|
||||
|
||||
## Support
|
||||
|
||||
For issues or questions:
|
||||
1. Check this documentation
|
||||
2. Review the troubleshooting section
|
||||
3. Create an issue on GitHub
|
||||
4. Contact Moko Consulting for professional support
|
||||
|
||||
## License
|
||||
|
||||
This feature is part of the MokoDoliCare module and is licensed under GPL v3.
|
||||
|
||||
---
|
||||
|
||||
**Version**: 1.1.0
|
||||
**Last Updated**: 2026-03-03
|
||||
**Author**: Moko Consulting
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,505 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliCare Roadmap
|
||||
|
||||
**Strategic Product Roadmap and Feature Timeline**
|
||||
|
||||
This document outlines the strategic direction and planned features for the MokoDoliCare Childcare Management Module. Our goal is to create the most comprehensive, secure, and user-friendly childcare management solution for Dolibarr.
|
||||
|
||||
---
|
||||
|
||||
## 📍 Current Status
|
||||
|
||||
**Version**: 1.1.0 (Released: March 2026)
|
||||
|
||||
### Released Features
|
||||
- ✅ Child record management with medical info and emergency contacts
|
||||
- ✅ Remote check-in/check-out system with parent authentication
|
||||
- ✅ Digital signature capture for check-in/check-out
|
||||
- ✅ Payroll time clock with parent accountability
|
||||
- ✅ Parent/guardian management with secure PIN authentication
|
||||
- ✅ Daily attendance tracking with timestamps
|
||||
- ✅ Activity scheduling and management
|
||||
- ✅ Basic reporting and statistics
|
||||
- ✅ Multi-entity support
|
||||
- ✅ Role-based permissions
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Product Vision
|
||||
|
||||
**Mission**: Empower childcare facilities with enterprise-grade management tools that save time, improve safety, and enhance parent communication - all within the trusted Dolibarr platform.
|
||||
|
||||
### Core Principles
|
||||
1. **Safety First**: Every feature prioritizes child safety and regulatory compliance
|
||||
2. **Parent-Centric**: Easy communication and transparency for parents
|
||||
3. **Staff Efficiency**: Reduce administrative burden with automation
|
||||
4. **Dolibarr Integration**: Seamless integration with existing Dolibarr workflows
|
||||
5. **Mobile-Ready**: Optimize for tablets and mobile devices
|
||||
6. **Data Privacy**: Protect sensitive child and family information
|
||||
|
||||
---
|
||||
|
||||
## 🗓️ Release Timeline
|
||||
|
||||
### Version 1.2.0 - Enhanced Communication (Q2 2026)
|
||||
**Theme**: Connecting parents and staff through better communication tools
|
||||
|
||||
**Target Release**: May 2026
|
||||
|
||||
#### Features
|
||||
- **Email Notifications for Parents**
|
||||
- Automated attendance confirmations
|
||||
- Activity updates and newsletters
|
||||
- Event reminders and announcements
|
||||
- Daily summary emails
|
||||
- Customizable notification preferences
|
||||
|
||||
- **SMS/Text Notifications** (Optional)
|
||||
- Check-in/check-out confirmations
|
||||
- Emergency alerts
|
||||
- Pickup reminders
|
||||
- Integration with popular SMS gateways
|
||||
|
||||
- **Parent Portal Enhancements**
|
||||
- View child's daily schedule
|
||||
- Access attendance history
|
||||
- Download monthly reports
|
||||
- Update contact information
|
||||
|
||||
- **Document Management Phase 1**
|
||||
- Upload and attach documents to child records
|
||||
- Store enrollment forms and agreements
|
||||
- Medical records and vaccination documents
|
||||
- Photo gallery for activities
|
||||
- Document version control
|
||||
|
||||
**Technical Goals**
|
||||
- Email templating system
|
||||
- Background job queue for notifications
|
||||
- Document storage integration
|
||||
- File upload security enhancements
|
||||
|
||||
---
|
||||
|
||||
### Version 1.3.0 - Advanced Operations (Q3 2026)
|
||||
**Theme**: Streamlining daily operations and staff management
|
||||
|
||||
**Target Release**: August 2026
|
||||
|
||||
#### Features
|
||||
- **Staff Scheduling and Management**
|
||||
- Staff roster creation
|
||||
- Shift planning and assignments
|
||||
- Time-off requests and approvals
|
||||
- Staff attendance tracking
|
||||
- Minimum staffing ratio alerts
|
||||
|
||||
- **Meal Planning and Nutritional Tracking**
|
||||
- Weekly/monthly meal planning
|
||||
- Nutritional information database
|
||||
- Allergen tracking and alerts
|
||||
- Meal consumption tracking per child
|
||||
- Dietary restriction management
|
||||
- Parent meal notifications
|
||||
|
||||
- **Medical Records and Vaccination Tracking**
|
||||
- Vaccination schedule templates
|
||||
- Vaccination due date reminders
|
||||
- Medical history tracking
|
||||
- Medication administration log
|
||||
- Illness tracking and reporting
|
||||
- Doctor and insurance information
|
||||
|
||||
- **Enhanced Activity Management**
|
||||
- Activity templates library
|
||||
- Lesson plans and curriculum tracking
|
||||
- Learning milestones and assessments
|
||||
- Photo/video attachments to activities
|
||||
- Parent sharing of activity photos
|
||||
|
||||
**Technical Goals**
|
||||
- Staff scheduling algorithm
|
||||
- Medical records encryption
|
||||
- Photo storage optimization
|
||||
- Activity template engine
|
||||
|
||||
---
|
||||
|
||||
### Version 1.4.0 - Reporting & Analytics (Q4 2026)
|
||||
**Theme**: Data-driven insights and compliance reporting
|
||||
|
||||
**Target Release**: November 2026
|
||||
|
||||
#### Features
|
||||
- **Advanced Reporting Dashboard**
|
||||
- Executive dashboard with KPIs
|
||||
- Attendance analytics and trends
|
||||
- Revenue and billing insights
|
||||
- Staff utilization reports
|
||||
- Child development tracking
|
||||
- Customizable report builder
|
||||
|
||||
- **Export and Integration**
|
||||
- PDF report generation
|
||||
- Excel export functionality
|
||||
- Chart and graph visualizations
|
||||
- Data export for accounting systems
|
||||
- API for third-party integrations
|
||||
|
||||
- **Compliance Reporting**
|
||||
- Licensing and regulatory reports
|
||||
- Incident and accident reports
|
||||
- Staff-to-child ratio monitoring
|
||||
- Health inspection documentation
|
||||
- Fire drill and safety logs
|
||||
|
||||
**Technical Goals**
|
||||
- Reporting engine development
|
||||
- Chart library integration
|
||||
- PDF generation optimization
|
||||
- REST API endpoints
|
||||
|
||||
---
|
||||
|
||||
### Version 2.0.0 - Financial Management (Q1 2027)
|
||||
**Theme**: Complete financial operations for childcare businesses
|
||||
|
||||
**Target Release**: February 2027
|
||||
|
||||
#### Major Features
|
||||
|
||||
##### Billing and Invoicing
|
||||
- **Invoice Generation for Childcare Fees**
|
||||
- Automated monthly/weekly billing
|
||||
- Hourly rate calculations from attendance
|
||||
- Flat rate and sliding scale pricing
|
||||
- Late fees and discounts
|
||||
- Multi-child discounts
|
||||
- Integration with Dolibarr invoicing
|
||||
|
||||
- **Payment Processing**
|
||||
- Online payment gateway integration
|
||||
- Credit card payment processing
|
||||
- ACH/bank transfers
|
||||
- Payment plans and schedules
|
||||
- Past-due account management
|
||||
- Payment reminder emails
|
||||
|
||||
- **Subsidy and Grant Management**
|
||||
- Government subsidy tracking
|
||||
- Scholarship management
|
||||
- Grant reporting and compliance
|
||||
- Co-payment calculations
|
||||
|
||||
##### Financial Reporting
|
||||
- Accounts receivable aging reports
|
||||
- Revenue forecasting
|
||||
- Profitability analysis by program
|
||||
- Budget vs. actual tracking
|
||||
- Tax reporting documentation
|
||||
|
||||
**Technical Goals**
|
||||
- Payment gateway integration (Stripe, PayPal)
|
||||
- Financial calculation engine
|
||||
- PCI compliance for payment data
|
||||
- Dolibarr accounting module integration
|
||||
|
||||
---
|
||||
|
||||
### Version 2.1.0 - Mobile Experience (Q2 2027)
|
||||
**Theme**: Mobile-first experience for parents and staff
|
||||
|
||||
**Target Release**: May 2027
|
||||
|
||||
#### Features
|
||||
- **Progressive Web App (PWA)**
|
||||
- Install as mobile app
|
||||
- Offline functionality
|
||||
- Push notifications
|
||||
- Fast, app-like experience
|
||||
|
||||
- **Mobile-Responsive Interface Improvements**
|
||||
- Redesigned mobile layouts
|
||||
- Touch-optimized interactions
|
||||
- Improved tablet check-in interface
|
||||
- Mobile-friendly reports
|
||||
|
||||
- **Native Mobile App** (Future consideration)
|
||||
- iOS and Android apps
|
||||
- Native performance
|
||||
- Camera integration for photos
|
||||
- Biometric authentication
|
||||
|
||||
**Technical Goals**
|
||||
- PWA implementation
|
||||
- Service worker for offline mode
|
||||
- Mobile UI framework
|
||||
- Push notification service
|
||||
|
||||
---
|
||||
|
||||
### Version 2.2.0 - Integration & Automation (Q3 2027)
|
||||
**Theme**: Connect with external systems and automate workflows
|
||||
|
||||
**Target Release**: August 2027
|
||||
|
||||
#### Features
|
||||
- **Calendar Integration**
|
||||
- Google Calendar sync
|
||||
- Microsoft Outlook integration
|
||||
- Apple Calendar support
|
||||
- Event and activity syncing
|
||||
- Shared calendars for parents
|
||||
|
||||
- **REST API Endpoints**
|
||||
- Complete API documentation
|
||||
- Authentication and authorization
|
||||
- Webhooks for events
|
||||
- Mobile app integration
|
||||
- Third-party system integration
|
||||
|
||||
- **Workflow Automation**
|
||||
- Automated enrollment workflows
|
||||
- Attendance reminders
|
||||
- Re-enrollment campaigns
|
||||
- Birthday notifications
|
||||
- License renewal reminders
|
||||
|
||||
**Technical Goals**
|
||||
- REST API development
|
||||
- OAuth 2.0 implementation
|
||||
- Webhook infrastructure
|
||||
- API rate limiting and monitoring
|
||||
|
||||
---
|
||||
|
||||
### Version 3.0.0 - Enterprise & Multi-Site (Q4 2027)
|
||||
**Theme**: Scaling for enterprise childcare organizations
|
||||
|
||||
**Target Release**: November 2027
|
||||
|
||||
#### Features
|
||||
- **Multi-Site Management**
|
||||
- Central dashboard for multiple facilities
|
||||
- Cross-site reporting and analytics
|
||||
- Centralized staff management
|
||||
- Resource sharing between sites
|
||||
- Consolidated billing
|
||||
|
||||
- **Waitlist Management**
|
||||
- Online enrollment application
|
||||
- Waitlist prioritization
|
||||
- Automated enrollment offers
|
||||
- Waitlist analytics
|
||||
|
||||
- **Advanced Security**
|
||||
- Two-factor authentication (2FA)
|
||||
- Single Sign-On (SSO) integration
|
||||
- Enhanced audit logging
|
||||
- Data retention policies
|
||||
- GDPR compliance tools
|
||||
|
||||
- **Marketing and CRM**
|
||||
- Lead tracking and nurturing
|
||||
- Tour scheduling and management
|
||||
- Marketing campaign management
|
||||
- Parent satisfaction surveys
|
||||
- Referral tracking
|
||||
|
||||
**Technical Goals**
|
||||
- Multi-tenant architecture optimization
|
||||
- SSO provider integration
|
||||
- Enhanced security framework
|
||||
- CRM module integration
|
||||
|
||||
---
|
||||
|
||||
## 🌟 Future Considerations (Post-3.0)
|
||||
|
||||
These features are on our long-term radar but not yet scheduled:
|
||||
|
||||
### Advanced Features
|
||||
- **AI-Powered Insights**
|
||||
- Predictive attendance patterns
|
||||
- Staff scheduling optimization
|
||||
- Revenue forecasting
|
||||
- Anomaly detection for safety
|
||||
|
||||
- **Learning Management System (LMS)**
|
||||
- Curriculum builder
|
||||
- Assessment tracking
|
||||
- Portfolio management
|
||||
- Parent-teacher conferences scheduling
|
||||
|
||||
- **Transportation Management**
|
||||
- Bus route planning
|
||||
- Driver assignments
|
||||
- Pick-up/drop-off tracking
|
||||
- GPS integration
|
||||
|
||||
- **Inventory Management**
|
||||
- Supplies and materials tracking
|
||||
- Automatic reorder alerts
|
||||
- Asset management
|
||||
- Vendor management
|
||||
|
||||
- **Emergency Management**
|
||||
- Emergency contact drills
|
||||
- Evacuation planning
|
||||
- Real-time emergency alerts
|
||||
- Incident command system integration
|
||||
|
||||
### International Features
|
||||
- **Multi-Language Support**
|
||||
- Spanish (Español)
|
||||
- French (Français)
|
||||
- German (Deutsch)
|
||||
- Portuguese (Português)
|
||||
- Additional languages based on demand
|
||||
|
||||
- **Localization**
|
||||
- Regional date/time formats
|
||||
- Currency localization
|
||||
- Compliance with local regulations
|
||||
- Cultural customization
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Feature Priority Matrix
|
||||
|
||||
### High Priority (Must Have)
|
||||
- Email notifications (v1.2.0)
|
||||
- Document management (v1.2.0)
|
||||
- Staff scheduling (v1.3.0)
|
||||
- Medical records (v1.3.0)
|
||||
- Billing and invoicing (v2.0.0)
|
||||
|
||||
### Medium Priority (Should Have)
|
||||
- Advanced reporting (v1.4.0)
|
||||
- Meal planning (v1.3.0)
|
||||
- Calendar integration (v2.2.0)
|
||||
- Mobile PWA (v2.1.0)
|
||||
- REST API (v2.2.0)
|
||||
|
||||
### Low Priority (Nice to Have)
|
||||
- SMS notifications (v1.2.0)
|
||||
- Native mobile apps (v2.1.0+)
|
||||
- Marketing CRM (v3.0.0)
|
||||
- Waitlist management (v3.0.0)
|
||||
- AI insights (Future)
|
||||
|
||||
---
|
||||
|
||||
## 📊 Success Metrics
|
||||
|
||||
We'll measure success through:
|
||||
|
||||
### Adoption Metrics
|
||||
- Number of active installations
|
||||
- Number of children managed
|
||||
- Number of daily check-ins
|
||||
- User satisfaction scores
|
||||
|
||||
### Usage Metrics
|
||||
- Parent portal engagement
|
||||
- Mobile vs. desktop usage
|
||||
- Feature adoption rates
|
||||
- Average session duration
|
||||
|
||||
### Business Metrics
|
||||
- Support ticket reduction
|
||||
- Time saved on administrative tasks
|
||||
- Parent retention rates
|
||||
- Revenue growth for customers
|
||||
|
||||
### Technical Metrics
|
||||
- System uptime (target: 99.9%)
|
||||
- Page load times (target: <2s)
|
||||
- API response times (target: <500ms)
|
||||
- Bug resolution time (target: <48h)
|
||||
|
||||
---
|
||||
|
||||
## 🤝 Community Input
|
||||
|
||||
We welcome community feedback on this roadmap!
|
||||
|
||||
### How to Contribute Ideas
|
||||
1. **GitHub Issues**: Submit feature requests
|
||||
2. **Community Forums**: Discuss features with other users
|
||||
3. **User Surveys**: Participate in our quarterly surveys
|
||||
4. **Beta Testing**: Sign up for early access to new features
|
||||
|
||||
### Voting on Features
|
||||
- Star feature requests on GitHub to vote
|
||||
- Most popular features may be prioritized
|
||||
- We balance community requests with strategic vision
|
||||
|
||||
---
|
||||
|
||||
## 📋 Development Process
|
||||
|
||||
### Release Cadence
|
||||
- **Major releases** (x.0.0): Quarterly with significant new features
|
||||
- **Minor releases** (x.x.0): Monthly with enhancements and fixes
|
||||
- **Patch releases** (x.x.x): As needed for critical bugs
|
||||
|
||||
### Quality Standards
|
||||
- All features must have documentation
|
||||
- Unit test coverage >80%
|
||||
- Security review for all features
|
||||
- User acceptance testing
|
||||
- Performance benchmarking
|
||||
|
||||
### Open Source Commitment
|
||||
- Transparent development on GitHub
|
||||
- Community code contributions welcome
|
||||
- Regular security audits
|
||||
- Responsive to bug reports
|
||||
|
||||
---
|
||||
|
||||
## 🔄 Roadmap Updates
|
||||
|
||||
This roadmap is a living document and will be updated:
|
||||
- **Quarterly**: Major roadmap reviews and updates
|
||||
- **Monthly**: Feature status updates
|
||||
- **As Needed**: For strategic shifts or major announcements
|
||||
|
||||
**Last Updated**: March 3, 2026
|
||||
**Next Review**: June 2026
|
||||
**Roadmap Version**: 1.0
|
||||
|
||||
---
|
||||
|
||||
## 📞 Questions or Suggestions?
|
||||
|
||||
Have ideas for features not on this roadmap? Want to discuss priorities?
|
||||
|
||||
- **Email**: support@mokoconsulting.tech
|
||||
- **GitHub Issues**: https://github.com/mokoconsulting-tech/MokoDoliCare/issues
|
||||
- **Documentation**: https://github.com/mokoconsulting-tech/MokoDoliCare/tree/main/docs
|
||||
|
||||
---
|
||||
|
||||
## See Also
|
||||
|
||||
- [Changelog](changelog.md) - Detailed version history
|
||||
- [Development Guide](development.md) - Contributing to the project
|
||||
- [Installation Guide](installation.md) - Getting started
|
||||
- [User Guide](user-guide.md) - Feature documentation
|
||||
|
||||
---
|
||||
|
||||
**Strategic Direction**: Building the future of childcare management, one feature at a time.
|
||||
|
||||
*This roadmap reflects our current plans and priorities. Features and timelines are subject to change based on community feedback, technical considerations, and strategic decisions.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,862 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Troubleshooting Guide
|
||||
|
||||
Comprehensive troubleshooting guide for MokoDoliCare Childcare Management Module. This guide covers common issues, error messages, and solutions.
|
||||
|
||||
## Table of Contents
|
||||
|
||||
1. [Installation Issues](#installation-issues)
|
||||
2. [Module Activation Problems](#module-activation-problems)
|
||||
3. [Database Issues](#database-issues)
|
||||
4. [Permission Problems](#permission-problems)
|
||||
5. [Data Entry Issues](#data-entry-issues)
|
||||
6. [Performance Issues](#performance-issues)
|
||||
7. [User Interface Problems](#user-interface-problems)
|
||||
8. [Error Messages](#error-messages)
|
||||
9. [Diagnostic Tools](#diagnostic-tools)
|
||||
|
||||
---
|
||||
|
||||
## Installation Issues
|
||||
|
||||
### Module Not Appearing in Module List
|
||||
|
||||
**Symptoms**:
|
||||
- Can't find "Childcare Management" in module list
|
||||
- Module list doesn't load
|
||||
|
||||
**Possible Causes & Solutions**:
|
||||
|
||||
#### 1. Files Not in Correct Location
|
||||
|
||||
**Check**:
|
||||
```bash
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/core/modules/
|
||||
```
|
||||
|
||||
**Expected**: `modMokoDoliCare.class.php` should exist
|
||||
|
||||
**Solution**:
|
||||
```bash
|
||||
# Copy files from src/ if they're in wrong location
|
||||
cp -r /path/to/MokoDoliCare/src/* /path/to/dolibarr/htdocs/custom/childcare/
|
||||
```
|
||||
|
||||
#### 2. Incorrect File Permissions
|
||||
|
||||
**Check**:
|
||||
```bash
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/
|
||||
```
|
||||
|
||||
**Should see**:
|
||||
- Directories: `755` (drwxr-xr-x)
|
||||
- Files: `644` (-rw-r--r--)
|
||||
- Owner: `www-data` (or your web server user)
|
||||
|
||||
**Solution**:
|
||||
```bash
|
||||
# Fix ownership
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/childcare/
|
||||
|
||||
# Fix permissions
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type d -exec chmod 755 {} \;
|
||||
find /path/to/dolibarr/htdocs/custom/childcare/ -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
#### 3. PHP Syntax Errors
|
||||
|
||||
**Check**:
|
||||
```bash
|
||||
php -l /path/to/dolibarr/htdocs/custom/childcare/core/modules/modMokoDoliCare.class.php
|
||||
```
|
||||
|
||||
**Expected**: "No syntax errors detected"
|
||||
|
||||
**If errors found**: Review the PHP error and fix syntax issues
|
||||
|
||||
#### 4. Cache Issues
|
||||
|
||||
**Solution**:
|
||||
```bash
|
||||
# Clear Dolibarr cache
|
||||
rm -rf /path/to/dolibarr/documents/install.lock
|
||||
|
||||
# Clear browser cache
|
||||
# Press Ctrl+Shift+Del (Chrome/Firefox)
|
||||
# Or use incognito/private mode
|
||||
```
|
||||
|
||||
### Installation Fails with "Include of main fails"
|
||||
|
||||
**Symptom**: Error message when accessing module files
|
||||
|
||||
**Cause**: Module can't find Dolibarr's main.inc.php
|
||||
|
||||
**Solution**:
|
||||
|
||||
1. **Verify Dolibarr Installation**:
|
||||
```bash
|
||||
ls -la /path/to/dolibarr/htdocs/main.inc.php
|
||||
```
|
||||
|
||||
2. **Check Module Location**:
|
||||
Must be in: `/path/to/dolibarr/htdocs/custom/childcare/`
|
||||
|
||||
3. **Check Dolibarr Configuration**:
|
||||
```php
|
||||
// In /path/to/dolibarr/htdocs/conf/conf.php
|
||||
$dolibarr_main_document_root_alt = '/path/to/dolibarr/htdocs/custom';
|
||||
$dolibarr_main_url_root_alt = '/custom';
|
||||
```
|
||||
|
||||
### Database Tables Not Created
|
||||
|
||||
**Symptoms**:
|
||||
- Module activates but doesn't work
|
||||
- Errors about missing tables
|
||||
|
||||
**Check**:
|
||||
```sql
|
||||
SHOW TABLES LIKE 'llx_childcare%';
|
||||
```
|
||||
|
||||
**Expected**: Should show 3 tables:
|
||||
- `llx_childcare_child`
|
||||
- `llx_childcare_attendance`
|
||||
- `llx_childcare_activity`
|
||||
|
||||
**Solution**:
|
||||
|
||||
1. **Manual Table Creation**:
|
||||
```bash
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_child.sql
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_attendance.sql
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_activity.sql
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_child.key.sql
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_attendance.key.sql
|
||||
mysql -u username -p database_name < /path/to/dolibarr/htdocs/custom/childcare/sql/llx_childcare_activity.key.sql
|
||||
```
|
||||
|
||||
2. **Check Database Permissions**:
|
||||
```sql
|
||||
SHOW GRANTS FOR 'dolibarr_user'@'localhost';
|
||||
```
|
||||
|
||||
Should include: `CREATE`, `ALTER`, `INDEX` privileges
|
||||
|
||||
---
|
||||
|
||||
## Module Activation Problems
|
||||
|
||||
### Can't Activate Module
|
||||
|
||||
**Symptom**: Click activate button but nothing happens or error appears
|
||||
|
||||
#### Solution 1: Check User Permissions
|
||||
|
||||
**Required**: Must be logged in as administrator
|
||||
|
||||
**Verify**:
|
||||
1. Go to **Home → Users & Groups → Your User**
|
||||
2. Check **Administrator** box is checked
|
||||
3. Verify **Super-administrator** rights if needed
|
||||
|
||||
#### Solution 2: Check for Conflicting Modules
|
||||
|
||||
Some modules may conflict. Check error logs:
|
||||
|
||||
```bash
|
||||
tail -f /path/to/dolibarr/documents/dolibarr.log
|
||||
```
|
||||
|
||||
Look for error messages when attempting activation
|
||||
|
||||
#### Solution 3: Database Connection Issues
|
||||
|
||||
```sql
|
||||
-- Check module constant
|
||||
SELECT * FROM llx_const WHERE name = 'MAIN_MODULE_CHILDCARE';
|
||||
|
||||
-- If exists but value = 0, manually set to 1
|
||||
UPDATE llx_const SET value = '1' WHERE name = 'MAIN_MODULE_CHILDCARE';
|
||||
|
||||
-- If doesn't exist, insert it
|
||||
INSERT INTO llx_const (name, value, type, note, entity)
|
||||
VALUES ('MAIN_MODULE_CHILDCARE', '1', 'chaine', 'Module childcare enabled', 1);
|
||||
```
|
||||
|
||||
### Module Activates But Menu Doesn't Appear
|
||||
|
||||
**Symptoms**:
|
||||
- Module shows as "Active"
|
||||
- No "Childcare" menu in top navigation
|
||||
|
||||
**Solutions**:
|
||||
|
||||
#### 1. Clear Cache and Refresh
|
||||
|
||||
```bash
|
||||
# Server-side
|
||||
rm -rf /path/to/dolibarr/documents/install.lock
|
||||
|
||||
# Client-side
|
||||
# Hard refresh browser: Ctrl+Shift+R (or Ctrl+F5)
|
||||
```
|
||||
|
||||
#### 2. Check User Permissions
|
||||
|
||||
User must have at least **Read** permission in Childcare module:
|
||||
|
||||
1. Go to **Home → Users & Groups → [Your User]**
|
||||
2. Click **Permissions** tab
|
||||
3. Find **Childcare** section
|
||||
4. Check at least one permission (e.g., "Read child records")
|
||||
5. Save
|
||||
|
||||
#### 3. Check Menu Configuration
|
||||
|
||||
```sql
|
||||
-- Verify menu entries
|
||||
SELECT * FROM llx_menu
|
||||
WHERE module = 'childcare'
|
||||
ORDER BY position;
|
||||
|
||||
-- If no results, menu may not be configured properly
|
||||
-- Deactivate and reactivate module
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Database Issues
|
||||
|
||||
### Foreign Key Constraint Errors
|
||||
|
||||
**Symptom**: Error when trying to delete records
|
||||
|
||||
**Error Message**: `Cannot delete or update a parent row: a foreign key constraint fails`
|
||||
|
||||
**Explanation**: Record has related records that must be deleted first
|
||||
|
||||
**Example**: Can't delete a child who has attendance records
|
||||
|
||||
**Solutions**:
|
||||
|
||||
#### Option 1: Delete Related Records First
|
||||
|
||||
```sql
|
||||
-- Find attendance records for child ID 5
|
||||
SELECT * FROM llx_childcare_attendance WHERE fk_child = 5;
|
||||
|
||||
-- Delete attendance records
|
||||
DELETE FROM llx_childcare_attendance WHERE fk_child = 5;
|
||||
|
||||
-- Now delete child
|
||||
DELETE FROM llx_childcare_child WHERE rowid = 5;
|
||||
```
|
||||
|
||||
#### Option 2: Deactivate Instead of Delete
|
||||
|
||||
Instead of deleting, set status to inactive:
|
||||
|
||||
```sql
|
||||
UPDATE llx_childcare_child SET status = 0 WHERE rowid = 5;
|
||||
```
|
||||
|
||||
### Duplicate Entry Errors
|
||||
|
||||
**Error Message**: `Duplicate entry 'CHILD001' for key 'ref'`
|
||||
|
||||
**Cause**: Reference number already exists
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Use Different Reference**:
|
||||
- Let system auto-generate reference
|
||||
- Use next number in sequence (CHILD002, CHILD003, etc.)
|
||||
|
||||
2. **Check Existing References**:
|
||||
```sql
|
||||
SELECT ref FROM llx_childcare_child ORDER BY ref;
|
||||
```
|
||||
|
||||
### Table Doesn't Exist Error
|
||||
|
||||
**Error Message**: `Table 'dolibarr_db.llx_childcare_child' doesn't exist`
|
||||
|
||||
**Cause**: Database tables not created during activation
|
||||
|
||||
**Solution**: See [Database Tables Not Created](#database-tables-not-created) above
|
||||
|
||||
### Character Encoding Issues
|
||||
|
||||
**Symptoms**:
|
||||
- Special characters display as `�` or garbled text
|
||||
- Names with accents don't save correctly
|
||||
|
||||
**Solution**:
|
||||
|
||||
```sql
|
||||
-- Check table encoding
|
||||
SHOW CREATE TABLE llx_childcare_child;
|
||||
|
||||
-- Should be UTF8
|
||||
-- If not, convert:
|
||||
ALTER TABLE llx_childcare_child CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
|
||||
ALTER TABLE llx_childcare_attendance CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
|
||||
ALTER TABLE llx_childcare_activity CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Permission Problems
|
||||
|
||||
### User Can't See Any Childcare Data
|
||||
|
||||
**Symptom**: Module menu appears but lists are empty or "Access Forbidden"
|
||||
|
||||
**Diagnosis**:
|
||||
|
||||
1. **Check User Has Permissions**:
|
||||
- Home → Users & Groups → [User] → Permissions tab
|
||||
- Look for Childcare section
|
||||
- At minimum need "Read" permission
|
||||
|
||||
2. **Check User is Active**:
|
||||
```sql
|
||||
SELECT login, statut FROM llx_user WHERE rowid = [user_id];
|
||||
```
|
||||
`statut` should be `1` (active)
|
||||
|
||||
3. **Check Multi-Entity Access**:
|
||||
If using multi-entity, user must have access to correct entity
|
||||
|
||||
**Solution**:
|
||||
|
||||
```sql
|
||||
-- Grant read permissions to user ID 5
|
||||
INSERT INTO llx_user_rights (fk_user, fk_id)
|
||||
VALUES
|
||||
(5, 18506501); -- Read child records
|
||||
|
||||
-- Or grant all childcare permissions
|
||||
INSERT INTO llx_user_rights (fk_user, fk_id)
|
||||
SELECT 5, 18506501 UNION ALL
|
||||
SELECT 5, 18506502 UNION ALL
|
||||
SELECT 5, 18506503 UNION ALL
|
||||
SELECT 5, 18506521 UNION ALL
|
||||
SELECT 5, 18506522 UNION ALL
|
||||
SELECT 5, 18506531 UNION ALL
|
||||
SELECT 5, 18506532;
|
||||
```
|
||||
|
||||
### Can See Data But Can't Edit
|
||||
|
||||
**Symptom**: User can view records but edit buttons are grayed out or missing
|
||||
|
||||
**Cause**: User has "Read" but not "Write" permission
|
||||
|
||||
**Solution**: Grant write permissions
|
||||
|
||||
1. Navigate to: **Home → Users & Groups → [User] → Permissions**
|
||||
2. In Childcare section, check:
|
||||
- ☑ Create/Edit child records
|
||||
- ☑ Create/Edit attendance
|
||||
- ☑ Create/Edit activities
|
||||
3. Click **Save**
|
||||
|
||||
### Permission Changes Don't Take Effect
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Force User to Re-login**:
|
||||
- Log out completely
|
||||
- Clear browser cookies
|
||||
- Log back in
|
||||
|
||||
2. **Clear Session Cache**:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/documents/sessions/*
|
||||
```
|
||||
|
||||
3. **Verify in Database**:
|
||||
```sql
|
||||
-- Check user's permissions
|
||||
SELECT ur.fk_id, r.label
|
||||
FROM llx_user_rights ur
|
||||
JOIN llx_rights_def r ON ur.fk_id = r.id
|
||||
WHERE ur.fk_user = [user_id]
|
||||
AND r.module = 'childcare';
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Data Entry Issues
|
||||
|
||||
### Can't Create New Child
|
||||
|
||||
**Symptom**: Save button doesn't work or error message appears
|
||||
|
||||
**Common Issues**:
|
||||
|
||||
#### 1. Required Fields Missing
|
||||
|
||||
**Required fields**:
|
||||
- First Name
|
||||
- Last Name
|
||||
- Date of Birth
|
||||
- Reference (if not auto-generated)
|
||||
|
||||
**Solution**: Fill in all required fields (marked with *)
|
||||
|
||||
#### 2. Invalid Date Format
|
||||
|
||||
**Error**: Date of birth invalid
|
||||
|
||||
**Correct Format**: YYYY-MM-DD (e.g., 2020-03-15)
|
||||
|
||||
**Solution**: Use date picker or enter in correct format
|
||||
|
||||
#### 3. Duplicate Reference
|
||||
|
||||
**Error**: "Reference already exists"
|
||||
|
||||
**Solution**:
|
||||
- Leave reference blank for auto-generation
|
||||
- Use unique reference number
|
||||
|
||||
### Dates Not Saving or Display Incorrectly
|
||||
|
||||
**Symptoms**:
|
||||
- Dates save as 0000-00-00
|
||||
- Dates display in wrong format
|
||||
- Times show wrong timezone
|
||||
|
||||
**Solutions**:
|
||||
|
||||
#### Check Date Format
|
||||
|
||||
```sql
|
||||
-- View date formats
|
||||
SELECT date_of_birth, enrollment_date FROM llx_childcare_child LIMIT 5;
|
||||
```
|
||||
|
||||
Should be: `2020-03-15` (not `03/15/2020` or `15-03-2020`)
|
||||
|
||||
#### Check Server Timezone
|
||||
|
||||
```bash
|
||||
# PHP timezone
|
||||
php -r "echo date_default_timezone_get();"
|
||||
|
||||
# MySQL timezone
|
||||
mysql -u user -p -e "SELECT @@global.time_zone, @@session.time_zone;"
|
||||
```
|
||||
|
||||
**Set in Dolibarr**:
|
||||
- Home → Setup → Other Setup → Timezone
|
||||
- Select correct timezone
|
||||
|
||||
### Check-In/Out Times Not Saving
|
||||
|
||||
**Symptoms**:
|
||||
- Times save as 00:00:00
|
||||
- Times display incorrectly
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Use 24-hour Format**:
|
||||
- Correct: `14:30` or `14:30:00`
|
||||
- Incorrect: `2:30 PM`
|
||||
|
||||
2. **Check Time Field in Database**:
|
||||
```sql
|
||||
SELECT check_in_time, check_out_time
|
||||
FROM llx_childcare_attendance
|
||||
WHERE attendance_date = CURDATE();
|
||||
```
|
||||
|
||||
3. **Verify Field Type**:
|
||||
```sql
|
||||
DESCRIBE llx_childcare_attendance;
|
||||
```
|
||||
`check_in_time` and `check_out_time` should be `time` type
|
||||
|
||||
---
|
||||
|
||||
## Performance Issues
|
||||
|
||||
### Slow Page Loading
|
||||
|
||||
**Symptoms**:
|
||||
- Pages take 5+ seconds to load
|
||||
- Timeout errors
|
||||
|
||||
**Diagnosis**:
|
||||
|
||||
```bash
|
||||
# Check PHP error log
|
||||
tail -f /var/log/apache2/error.log | grep childcare
|
||||
|
||||
# Check MySQL slow query log
|
||||
mysql -u root -p -e "SELECT * FROM mysql.slow_log WHERE sql_text LIKE '%childcare%' ORDER BY start_time DESC LIMIT 10;"
|
||||
```
|
||||
|
||||
**Solutions**:
|
||||
|
||||
#### 1. Database Optimization
|
||||
|
||||
```sql
|
||||
-- Analyze tables
|
||||
ANALYZE TABLE llx_childcare_child;
|
||||
ANALYZE TABLE llx_childcare_attendance;
|
||||
ANALYZE TABLE llx_childcare_activity;
|
||||
|
||||
-- Optimize tables
|
||||
OPTIMIZE TABLE llx_childcare_child;
|
||||
OPTIMIZE TABLE llx_childcare_attendance;
|
||||
OPTIMIZE TABLE llx_childcare_activity;
|
||||
```
|
||||
|
||||
#### 2. Check Index Usage
|
||||
|
||||
```sql
|
||||
-- Verify indexes exist
|
||||
SHOW INDEX FROM llx_childcare_child;
|
||||
SHOW INDEX FROM llx_childcare_attendance;
|
||||
SHOW INDEX FROM llx_childcare_activity;
|
||||
```
|
||||
|
||||
#### 3. PHP Memory and Execution Time
|
||||
|
||||
```php
|
||||
// Check in Home → Setup → Other Setup → System
|
||||
// Or edit php.ini
|
||||
memory_limit = 512M
|
||||
max_execution_time = 300
|
||||
```
|
||||
|
||||
### Large Database Size
|
||||
|
||||
**Check Database Size**:
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
table_name,
|
||||
ROUND(((data_length + index_length) / 1024 / 1024), 2) AS "Size (MB)",
|
||||
table_rows
|
||||
FROM information_schema.TABLES
|
||||
WHERE table_schema = 'dolibarr_db'
|
||||
AND table_name LIKE 'llx_childcare%'
|
||||
ORDER BY (data_length + index_length) DESC;
|
||||
```
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Archive Old Data**:
|
||||
```sql
|
||||
-- Archive attendance older than 2 years
|
||||
CREATE TABLE llx_childcare_attendance_archive
|
||||
AS SELECT * FROM llx_childcare_attendance
|
||||
WHERE attendance_date < DATE_SUB(CURDATE(), INTERVAL 2 YEAR);
|
||||
|
||||
-- Delete from main table after verification
|
||||
DELETE FROM llx_childcare_attendance
|
||||
WHERE attendance_date < DATE_SUB(CURDATE(), INTERVAL 2 YEAR);
|
||||
```
|
||||
|
||||
2. **Delete Unnecessary Data**:
|
||||
```sql
|
||||
-- Delete cancelled activities older than 1 year
|
||||
DELETE FROM llx_childcare_activity
|
||||
WHERE status = 0
|
||||
AND activity_date < DATE_SUB(CURDATE(), INTERVAL 1 YEAR);
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## User Interface Problems
|
||||
|
||||
### Menu Items Missing
|
||||
|
||||
**Symptom**: Some menu items don't appear
|
||||
|
||||
**Check**:
|
||||
1. User permissions (need appropriate rights)
|
||||
2. Browser cache (clear and refresh)
|
||||
3. Module fully activated
|
||||
|
||||
### Page Layout Broken
|
||||
|
||||
**Symptoms**:
|
||||
- CSS not loading
|
||||
- Elements overlapping
|
||||
- Responsive design not working
|
||||
|
||||
**Solutions**:
|
||||
|
||||
1. **Clear Browser Cache**: Ctrl+Shift+Del
|
||||
|
||||
2. **Check CSS Files Exist**:
|
||||
```bash
|
||||
ls -la /path/to/dolibarr/htdocs/custom/childcare/css/
|
||||
```
|
||||
|
||||
3. **Check for JavaScript Errors**:
|
||||
- Open browser Developer Tools (F12)
|
||||
- Check Console tab for errors
|
||||
|
||||
4. **Verify File Permissions**:
|
||||
```bash
|
||||
chmod 644 /path/to/dolibarr/htdocs/custom/childcare/css/*.css
|
||||
```
|
||||
|
||||
### Dropdown Lists Empty
|
||||
|
||||
**Symptom**: Child selection dropdown is empty
|
||||
|
||||
**Causes**:
|
||||
|
||||
1. **No Active Children**:
|
||||
```sql
|
||||
SELECT COUNT(*) FROM llx_childcare_child WHERE status = 1;
|
||||
```
|
||||
|
||||
2. **Wrong Entity** (multi-entity setups):
|
||||
```sql
|
||||
SELECT * FROM llx_childcare_child WHERE entity = [your_entity_id];
|
||||
```
|
||||
|
||||
3. **JavaScript Error**: Check browser console (F12)
|
||||
|
||||
---
|
||||
|
||||
## Error Messages
|
||||
|
||||
### "Access Forbidden"
|
||||
|
||||
**Full Message**: "Access to this area is forbidden. You are logged in but do not have permission..."
|
||||
|
||||
**Cause**: User lacks required permissions
|
||||
|
||||
**Solution**: See [Permission Problems](#permission-problems)
|
||||
|
||||
### "Table doesn't exist"
|
||||
|
||||
**Full Message**: "Table 'dolibarr_db.llx_childcare_child' doesn't exist"
|
||||
|
||||
**Solution**: See [Table Doesn't Exist Error](#table-doesnt-exist-error)
|
||||
|
||||
### "Cannot add or update a child row"
|
||||
|
||||
**Full Message**: "Cannot add or update a child row: a foreign key constraint fails"
|
||||
|
||||
**Cause**: Trying to reference non-existent record
|
||||
|
||||
**Example**: Creating attendance for child ID that doesn't exist
|
||||
|
||||
**Solution**:
|
||||
```sql
|
||||
-- Verify child exists
|
||||
SELECT * FROM llx_childcare_child WHERE rowid = [child_id];
|
||||
|
||||
-- If doesn't exist, create child first
|
||||
```
|
||||
|
||||
### "Duplicate entry"
|
||||
|
||||
**Full Message**: "Duplicate entry 'CHILD001' for key 'ref'"
|
||||
|
||||
**Solution**: See [Duplicate Entry Errors](#duplicate-entry-errors)
|
||||
|
||||
### "Out of memory"
|
||||
|
||||
**Full Message**: "Allowed memory size of 134217728 bytes exhausted"
|
||||
|
||||
**Solution**:
|
||||
|
||||
```php
|
||||
// Increase PHP memory limit
|
||||
// In php.ini or conf/conf.php
|
||||
memory_limit = 512M
|
||||
```
|
||||
|
||||
```bash
|
||||
# Restart web server
|
||||
sudo systemctl restart apache2
|
||||
# or
|
||||
sudo systemctl restart nginx
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Diagnostic Tools
|
||||
|
||||
### System Information
|
||||
|
||||
```bash
|
||||
# Dolibarr version
|
||||
cat /path/to/dolibarr/htdocs/filefunc.inc.php | grep DOL_VERSION
|
||||
|
||||
# PHP version and modules
|
||||
php -v
|
||||
php -m
|
||||
|
||||
# Database version
|
||||
mysql --version
|
||||
|
||||
# Disk space
|
||||
df -h
|
||||
|
||||
# Memory usage
|
||||
free -h
|
||||
```
|
||||
|
||||
### Module Status Check
|
||||
|
||||
```sql
|
||||
-- Module activation status
|
||||
SELECT * FROM llx_const WHERE name = 'MAIN_MODULE_CHILDCARE';
|
||||
|
||||
-- Module version
|
||||
SELECT * FROM llx_const WHERE name LIKE '%CHILDCARE%';
|
||||
|
||||
-- Tables exist
|
||||
SHOW TABLES LIKE 'llx_childcare%';
|
||||
|
||||
-- Record counts
|
||||
SELECT
|
||||
'children' as table_name, COUNT(*) as count FROM llx_childcare_child
|
||||
UNION ALL
|
||||
SELECT 'attendance', COUNT(*) FROM llx_childcare_attendance
|
||||
UNION ALL
|
||||
SELECT 'activities', COUNT(*) FROM llx_childcare_activity;
|
||||
```
|
||||
|
||||
### Log Files
|
||||
|
||||
```bash
|
||||
# Apache error log
|
||||
tail -f /var/log/apache2/error.log
|
||||
|
||||
# Nginx error log
|
||||
tail -f /var/log/nginx/error.log
|
||||
|
||||
# Dolibarr log
|
||||
tail -f /path/to/dolibarr/documents/dolibarr.log
|
||||
|
||||
# MySQL error log
|
||||
tail -f /var/log/mysql/error.log
|
||||
|
||||
# PHP error log
|
||||
tail -f /var/log/php/error.log
|
||||
```
|
||||
|
||||
### Debug Mode
|
||||
|
||||
Enable Dolibarr debug mode:
|
||||
|
||||
```php
|
||||
// In /path/to/dolibarr/htdocs/conf/conf.php
|
||||
$dolibarr_main_prod = 0; // 0 = debug mode, 1 = production mode
|
||||
```
|
||||
|
||||
**Warning**: Only use debug mode temporarily. Always return to production mode.
|
||||
|
||||
---
|
||||
|
||||
## Getting Additional Help
|
||||
|
||||
### Before Asking for Help
|
||||
|
||||
Gather this information:
|
||||
|
||||
1. **System Information**:
|
||||
- Dolibarr version
|
||||
- PHP version
|
||||
- Database type and version
|
||||
- Web server type and version
|
||||
|
||||
2. **Error Details**:
|
||||
- Exact error message
|
||||
- Steps to reproduce
|
||||
- When did it start happening
|
||||
- What changed recently
|
||||
|
||||
3. **Log Files**:
|
||||
- Relevant error log entries
|
||||
- Timestamps of issues
|
||||
|
||||
### Support Channels
|
||||
|
||||
1. **Documentation**:
|
||||
- [User Guide](user-guide.md)
|
||||
- [Admin Guide](admin-guide.md)
|
||||
- [Database Schema](database-schema.md)
|
||||
|
||||
2. **Community Support**:
|
||||
- GitHub Issues: Report bugs or feature requests
|
||||
- Dolibarr Forum: Community help
|
||||
|
||||
3. **Professional Support**:
|
||||
- Contact Moko Consulting for professional support
|
||||
|
||||
---
|
||||
|
||||
## Appendix: Quick Reference Commands
|
||||
|
||||
### Database Backup
|
||||
|
||||
```bash
|
||||
mysqldump -u user -p dolibarr_db \
|
||||
llx_childcare_child \
|
||||
llx_childcare_attendance \
|
||||
llx_childcare_activity > backup.sql
|
||||
```
|
||||
|
||||
### Database Restore
|
||||
|
||||
```bash
|
||||
mysql -u user -p dolibarr_db < backup.sql
|
||||
```
|
||||
|
||||
### Check Module Active
|
||||
|
||||
```bash
|
||||
mysql -u user -p dolibarr_db -e "SELECT value FROM llx_const WHERE name='MAIN_MODULE_CHILDCARE';"
|
||||
```
|
||||
|
||||
### Reset Module
|
||||
|
||||
```bash
|
||||
# Deactivate
|
||||
mysql -u user -p dolibarr_db -e "UPDATE llx_const SET value='0' WHERE name='MAIN_MODULE_CHILDCARE';"
|
||||
|
||||
# Reactivate (via Dolibarr UI or)
|
||||
mysql -u user -p dolibarr_db -e "UPDATE llx_const SET value='1' WHERE name='MAIN_MODULE_CHILDCARE';"
|
||||
```
|
||||
|
||||
### Clear All Data (DANGER!)
|
||||
|
||||
```sql
|
||||
-- WARNING: This deletes ALL childcare data!
|
||||
-- Backup first!
|
||||
TRUNCATE TABLE llx_childcare_attendance;
|
||||
TRUNCATE TABLE llx_childcare_activity;
|
||||
TRUNCATE TABLE llx_childcare_child;
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: 2026-02-19
|
||||
**Version**: 1.0.0
|
||||
**For**: MokoDoliCare Childcare Management Module
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliCare/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,863 @@
|
||||
← [Home](Home)
|
||||
|
||||
# User Guide
|
||||
|
||||
Complete guide to using MokoDoliCare for childcare facility management. This guide covers all features and workflows for daily operations.
|
||||
|
||||
## Table of Contents
|
||||
|
||||
1. [Getting Started](#getting-started)
|
||||
2. [Child Management](#child-management)
|
||||
3. [Attendance Tracking](#attendance-tracking)
|
||||
4. [Activity Management](#activity-management)
|
||||
5. [Reports and Analytics](#reports-and-analytics)
|
||||
6. [Daily Workflows](#daily-workflows)
|
||||
7. [Tips and Best Practices](#tips-and-best-practices)
|
||||
|
||||
---
|
||||
|
||||
## Getting Started
|
||||
|
||||
### Accessing MokoDoliCare
|
||||
|
||||
1. **Log in** to your Dolibarr installation
|
||||
2. Look for **"Childcare"** in the top navigation menu
|
||||
3. Click to access the childcare dashboard
|
||||
|
||||
### Dashboard Overview
|
||||
|
||||
The dashboard provides an at-a-glance view of:
|
||||
- 📊 **Total Active Children** - Current enrollment count
|
||||
- 📅 **Today's Attendance** - Present/Absent status
|
||||
- 🎯 **Scheduled Activities** - Today's activity schedule
|
||||
- 📈 **Recent Updates** - Latest changes and additions
|
||||
|
||||
### Navigation Menu
|
||||
|
||||
```
|
||||
Childcare
|
||||
├── Dashboard → Overview and statistics
|
||||
├── Children → Manage child records
|
||||
│ ├── List → View all children
|
||||
│ └── New Child → Add new child
|
||||
├── Attendance → Track daily attendance
|
||||
│ ├── List → View attendance records
|
||||
│ └── New Record → Record attendance
|
||||
└── Activities → Manage activities
|
||||
├── Schedule → View activity schedule
|
||||
└── New Activity → Create new activity
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Child Management
|
||||
|
||||
### Adding a New Child
|
||||
|
||||
#### Step-by-Step Process
|
||||
|
||||
1. Navigate to **Childcare → Children → New Child**
|
||||
2. Fill in the required information
|
||||
3. Click **Create** to save
|
||||
|
||||
#### Required Fields
|
||||
|
||||
| Field | Description | Example |
|
||||
|-------|-------------|---------|
|
||||
| **Reference** | Unique identifier (auto-generated if blank) | `CHILD001` |
|
||||
| **First Name** | Child's given name | `Emma` |
|
||||
| **Last Name** | Child's family name | `Johnson` |
|
||||
| **Date of Birth** | Birth date (YYYY-MM-DD) | `2020-03-15` |
|
||||
|
||||
#### Optional but Important Fields
|
||||
|
||||
| Field | Description | Best Practices |
|
||||
|-------|-------------|----------------|
|
||||
| **Gender** | Child's gender | Use for statistics; optional |
|
||||
| **Allergies** | Food/environmental allergies | ⚠️ Be specific and include severity |
|
||||
| **Medical Notes** | Health conditions, medications | Include emergency procedures |
|
||||
| **Emergency Contact** | Emergency contact info | Name, relationship, phone number |
|
||||
| **Enrollment Date** | When child started | Used for enrollment tracking |
|
||||
| **Status** | Active/Inactive | Check "Active" for current students |
|
||||
| **Public Notes** | Notes visible to all staff | General information |
|
||||
| **Private Notes** | Confidential notes | Restricted access |
|
||||
|
||||
#### Example: Complete Child Record
|
||||
|
||||
```
|
||||
Reference: CHILD001
|
||||
First Name: Emma
|
||||
Last Name: Johnson
|
||||
Date of Birth: March 15, 2020 (Age: 5 years)
|
||||
Gender: Female
|
||||
|
||||
Allergies:
|
||||
- Peanut allergy (SEVERE - EpiPen required in red bag)
|
||||
- Mild lactose intolerance (can have small amounts)
|
||||
|
||||
Medical Notes:
|
||||
- Asthma (uses blue inhaler as needed - in office)
|
||||
- Regular checkups with Dr. Smith at City Pediatrics
|
||||
- No other medical conditions
|
||||
|
||||
Emergency Contact:
|
||||
Primary: Sarah Johnson (Mother) - (555) 123-4567
|
||||
Secondary: Mike Johnson (Father) - (555) 123-4568
|
||||
Emergency: Grandma Susan - (555) 123-4569
|
||||
|
||||
Enrollment Date: September 1, 2023
|
||||
Status: ✓ Active
|
||||
```
|
||||
|
||||
### Viewing Child Records
|
||||
|
||||
#### Children List View
|
||||
|
||||
**Navigation**: Childcare → Children → List
|
||||
|
||||
**Features**:
|
||||
- **Search bar** - Find children by name or reference
|
||||
- **Filter by status** - Active, Inactive, or All
|
||||
- **Sort options** - By name, enrollment date, or status
|
||||
- **Quick actions** - Edit, view, or delete from list
|
||||
|
||||
**List Columns**:
|
||||
| Column | Description |
|
||||
|--------|-------------|
|
||||
| Ref | Child reference number |
|
||||
| Name | Full name (First Last) |
|
||||
| Date of Birth | Birth date and calculated age |
|
||||
| Status | Active/Inactive indicator |
|
||||
| Actions | Edit, View, Delete buttons |
|
||||
|
||||
#### Child Card View
|
||||
|
||||
**Navigation**: Click on child name from list
|
||||
|
||||
**Tabs**:
|
||||
1. **Overview** - Basic information and status
|
||||
2. **Attendance** - Historical attendance records
|
||||
3. **Medical** - Allergies and medical information
|
||||
4. **Contacts** - Emergency contacts and guardians
|
||||
5. **Notes** - Public and private notes
|
||||
|
||||
### Editing Child Information
|
||||
|
||||
1. Go to **Children → List**
|
||||
2. Click on the child's name or click **Edit** button
|
||||
3. Modify the information
|
||||
4. Click **Save** to update
|
||||
|
||||
**Important**: Changes are logged with timestamp and user who made the change.
|
||||
|
||||
### Deactivating a Child
|
||||
|
||||
When a child leaves the facility:
|
||||
|
||||
1. Open the child's record
|
||||
2. Uncheck **"Active"** status
|
||||
3. Add note with departure date and reason (optional)
|
||||
4. Click **Save**
|
||||
|
||||
**Note**: Deactivating preserves all historical data but removes child from active lists.
|
||||
|
||||
### Searching and Filtering
|
||||
|
||||
#### Search by Name
|
||||
```
|
||||
Search box: "Emma" → Shows all Emmas
|
||||
Search box: "John" → Shows Johns and Johnsons
|
||||
```
|
||||
|
||||
#### Filter Options
|
||||
- **Status**: Active / Inactive / All
|
||||
- **Enrollment Date**: This Year / Last Year / All Time
|
||||
- **Age Range**: Infants / Toddlers / Preschool / All
|
||||
|
||||
#### Advanced Search Tips
|
||||
- Use reference numbers for exact matches: `CHILD001`
|
||||
- Search by partial names: `Joh` finds `Johnson`, `John`, `Johnny`
|
||||
- Combine filters: Active + This Year = Current year enrollees
|
||||
|
||||
---
|
||||
|
||||
## Attendance Tracking
|
||||
|
||||
### Recording Daily Attendance
|
||||
|
||||
#### Quick Check-In Process
|
||||
|
||||
**Morning Arrival**:
|
||||
|
||||
1. Go to **Childcare → Attendance → New Record**
|
||||
2. Select child from dropdown
|
||||
3. Date auto-fills to today
|
||||
4. Enter **Check-in Time** (e.g., `08:30`)
|
||||
5. Status: **Present** (default)
|
||||
6. Add morning notes (optional): `Brought show-and-tell item`
|
||||
7. Click **Save**
|
||||
|
||||
**Alternative Quick Method**:
|
||||
- From **Attendance List**, click **Quick Check-In**
|
||||
- Select multiple children
|
||||
- Bulk check-in with same time
|
||||
|
||||
#### Recording Check-Out
|
||||
|
||||
**Afternoon Departure**:
|
||||
|
||||
1. Go to **Attendance → List**
|
||||
2. Find today's record for the child
|
||||
3. Click **Edit**
|
||||
4. Enter **Check-out Time** (e.g., `15:30`)
|
||||
5. Add afternoon notes: `Had a great day. Ate all lunch.`
|
||||
6. Click **Save**
|
||||
|
||||
### Attendance Status Codes
|
||||
|
||||
| Status | Value | Use When |
|
||||
|--------|-------|----------|
|
||||
| **Present** | 1 | Child attended full or partial day |
|
||||
| **Absent** | 0 | Child did not attend (sick, vacation, etc.) |
|
||||
| **Partial** | 2 | Child attended only part of scheduled time |
|
||||
|
||||
### Daily Notes Best Practices
|
||||
|
||||
Good daily notes help parents and document child development:
|
||||
|
||||
**Structure Your Notes**:
|
||||
|
||||
```
|
||||
Morning:
|
||||
- Mood on arrival: Happy, excited
|
||||
- Items brought: Blue backpack, water bottle
|
||||
|
||||
Midday:
|
||||
- Meals: Ate all lunch, drank juice
|
||||
- Activities: Participated in art project, outdoor play
|
||||
- Nap: Slept 1.5 hours (12:30-2:00)
|
||||
|
||||
Afternoon:
|
||||
- Behavior: Played well with others, shared toys
|
||||
- Incidents: Small scrape on knee (cleaned, bandaid applied)
|
||||
- Departure: Left with grandmother at 3:30 PM
|
||||
```
|
||||
|
||||
**Example Excellent Daily Note**:
|
||||
|
||||
```
|
||||
Emma had a wonderful day! She arrived happy at 8:30 AM with her
|
||||
stuffed bear for show-and-tell. She ate all of her lunch and tried
|
||||
new carrots. She participated enthusiastically in our art project
|
||||
(painting will come home tomorrow). Napped well from 12:30-2:00 PM.
|
||||
Played nicely with friends during outdoor time. Small scrape on right
|
||||
knee from playground - cleaned and bandaid applied, no tears.
|
||||
Departed happy with mom at 3:45 PM.
|
||||
```
|
||||
|
||||
### Attendance Reports
|
||||
|
||||
#### View Attendance History
|
||||
|
||||
**For One Child**:
|
||||
1. Open child's card
|
||||
2. Click **Attendance** tab
|
||||
3. View full history with notes
|
||||
|
||||
**For All Children**:
|
||||
1. Go to **Attendance → List**
|
||||
2. Filter by date range
|
||||
3. Export to PDF or Excel (if available)
|
||||
|
||||
#### Common Attendance Reports
|
||||
|
||||
**Today's Attendance Summary**:
|
||||
- Total Present: 15
|
||||
- Total Absent: 3
|
||||
- Not Yet Recorded: 2
|
||||
- Attendance Rate: 83.3%
|
||||
|
||||
**Monthly Attendance**:
|
||||
- Total Days: 20
|
||||
- Average Daily Attendance: 16.5
|
||||
- Most Absent Day: Friday
|
||||
- Perfect Attendance: 8 children
|
||||
|
||||
### Late Check-In/Early Check-Out
|
||||
|
||||
Document timing issues:
|
||||
|
||||
1. Record actual check-in/out time
|
||||
2. Add note explaining: `Late arrival - parent called ahead`
|
||||
3. Track patterns for parent discussions if needed
|
||||
|
||||
### Handling Special Situations
|
||||
|
||||
#### Child is Absent
|
||||
|
||||
1. Create attendance record
|
||||
2. Select child and date
|
||||
3. Set Status: **Absent**
|
||||
4. Leave check-in/out times blank
|
||||
5. Add reason if known: `Sick - parent called`
|
||||
6. Click **Save**
|
||||
|
||||
#### Half-Day Attendance
|
||||
|
||||
1. Record check-in time
|
||||
2. Record check-out time (earlier than usual)
|
||||
3. Set Status: **Partial**
|
||||
4. Add note: `Half day - doctor appointment at 12:00`
|
||||
|
||||
#### Forgot to Record
|
||||
|
||||
You can always add historical records:
|
||||
1. Select the past date
|
||||
2. Enter check-in/out times
|
||||
3. Add note: `Retroactive entry - forgot to record`
|
||||
|
||||
---
|
||||
|
||||
## Activity Management
|
||||
|
||||
### Planning Activities
|
||||
|
||||
#### Creating a New Activity
|
||||
|
||||
1. Navigate to **Childcare → Activities → New Activity**
|
||||
2. Fill in the details:
|
||||
|
||||
| Field | Required | Example |
|
||||
|-------|----------|---------|
|
||||
| **Reference** | No (auto) | `ACT-2026-02-19-001` |
|
||||
| **Label** | Yes | `Morning Circle Time` |
|
||||
| **Description** | No | `Songs, weather, calendar, sharing` |
|
||||
| **Date** | Yes | `2026-02-19` |
|
||||
| **Time** | No | `09:00` |
|
||||
| **Activity Type** | No | `Learning` |
|
||||
| **Status** | Yes | `Scheduled` |
|
||||
|
||||
3. Click **Create**
|
||||
|
||||
### Activity Types Guide
|
||||
|
||||
#### Learning Activities
|
||||
|
||||
**Purpose**: Educational and developmental activities
|
||||
|
||||
**Examples**:
|
||||
- ABC and letter recognition
|
||||
- Number counting and math concepts
|
||||
- Shape and color identification
|
||||
- Science experiments
|
||||
- Puzzles and problem-solving
|
||||
- Calendar and weather learning
|
||||
|
||||
**Documentation**:
|
||||
```
|
||||
Label: Alphabet Practice
|
||||
Description: Practiced letters A-E using flashcards and songs
|
||||
Type: Learning
|
||||
Duration: 20 minutes
|
||||
Participation: 12 of 15 children
|
||||
Notes: Emma and Jacob excelled, Tommy needs more practice with letter C
|
||||
```
|
||||
|
||||
#### Play Activities
|
||||
|
||||
**Purpose**: Free or structured playtime
|
||||
|
||||
**Examples**:
|
||||
- Building blocks
|
||||
- Dramatic play (kitchen, dress-up)
|
||||
- Board games
|
||||
- Toy vehicles and figures
|
||||
- Sensory play (sand, water)
|
||||
- Indoor gym time
|
||||
|
||||
**Tips**:
|
||||
- Rotate toys weekly to maintain interest
|
||||
- Document social interactions
|
||||
- Note emerging friendships
|
||||
- Record any conflicts and resolutions
|
||||
|
||||
#### Outdoor Activities
|
||||
|
||||
**Purpose**: Physical exercise and fresh air
|
||||
|
||||
**Examples**:
|
||||
- Playground time
|
||||
- Nature walks
|
||||
- Ball games
|
||||
- Riding toys (tricycles, scooters)
|
||||
- Gardening
|
||||
- Chalk drawing
|
||||
|
||||
**Safety Notes**:
|
||||
- Always document weather conditions
|
||||
- Note any injuries immediately
|
||||
- Record sunscreen application
|
||||
- Document water intake on hot days
|
||||
|
||||
#### Arts & Crafts
|
||||
|
||||
**Purpose**: Creative expression and fine motor skills
|
||||
|
||||
**Examples**:
|
||||
- Painting (watercolor, finger, brush)
|
||||
- Drawing and coloring
|
||||
- Collage and cutting
|
||||
- Clay or playdough
|
||||
- Seasonal crafts
|
||||
- Parent gift projects
|
||||
|
||||
**Documentation**:
|
||||
```
|
||||
Label: Spring Flower Painting
|
||||
Description: Watercolor flowers using sponges and stamps
|
||||
Materials: Paper, watercolors, sponges, stamps
|
||||
Type: Arts
|
||||
Outcome: All paintings will dry and go home tomorrow
|
||||
Notes: Emma loved mixing colors, Jacob made a purple flower
|
||||
```
|
||||
|
||||
#### Music Activities
|
||||
|
||||
**Purpose**: Rhythm, movement, and auditory development
|
||||
|
||||
**Examples**:
|
||||
- Group singing
|
||||
- Musical instruments
|
||||
- Dance and movement
|
||||
- Listening to music
|
||||
- Rhythm games
|
||||
- Music and story combination
|
||||
|
||||
#### Story Time
|
||||
|
||||
**Purpose**: Language development and imagination
|
||||
|
||||
**Examples**:
|
||||
- Picture books
|
||||
- Chapter book readings (for older children)
|
||||
- Storytelling (without books)
|
||||
- Puppet shows
|
||||
- Children retelling stories
|
||||
- Author studies
|
||||
|
||||
**Best Practices**:
|
||||
```
|
||||
Label: "The Very Hungry Caterpillar" Story Time
|
||||
Books Read:
|
||||
- The Very Hungry Caterpillar (Eric Carle)
|
||||
- Follow-up: Lifecycle discussion
|
||||
Type: Story Time
|
||||
Duration: 15 minutes
|
||||
Engagement: High - children participated in counting fruits
|
||||
Notes: Will create butterfly craft tomorrow as follow-up
|
||||
```
|
||||
|
||||
#### Meal Times
|
||||
|
||||
**Purpose**: Nutrition and social skills
|
||||
|
||||
**Types**:
|
||||
- Breakfast
|
||||
- Morning snack
|
||||
- Lunch
|
||||
- Afternoon snack
|
||||
|
||||
**Documentation**:
|
||||
```
|
||||
Label: Lunch Time
|
||||
Type: Meals
|
||||
Menu:
|
||||
- Chicken nuggets
|
||||
- Carrot sticks
|
||||
- Apple slices
|
||||
- Milk
|
||||
Notes:
|
||||
- Emma ate all lunch
|
||||
- Jacob refused carrots (gave extra apples)
|
||||
- Tommy spilled milk (cleaned up, refilled)
|
||||
- New child Sarah ate well on first day
|
||||
```
|
||||
|
||||
#### Nap/Rest Time
|
||||
|
||||
**Purpose**: Physical rest and recovery
|
||||
|
||||
**Documentation**:
|
||||
```
|
||||
Label: Afternoon Nap Time
|
||||
Type: Naps
|
||||
Time: 12:30 PM - 2:30 PM
|
||||
Notes:
|
||||
- 14 of 15 children slept
|
||||
- Emma awoke after 45 minutes (looked at books quietly)
|
||||
- Jacob slept full 2 hours
|
||||
- Room temp: 70°F, lights dimmed, soft music
|
||||
```
|
||||
|
||||
### Activity Scheduling
|
||||
|
||||
#### Daily Schedule Template
|
||||
|
||||
```
|
||||
08:00 - 08:30 Arrival & Free Play
|
||||
08:30 - 09:00 Breakfast
|
||||
09:00 - 09:30 Morning Circle Time (Learning)
|
||||
09:30 - 10:30 Outdoor Play (Outdoor)
|
||||
10:30 - 11:00 Snack Time (Meals)
|
||||
11:00 - 12:00 Learning Activity (Learning)
|
||||
12:00 - 12:30 Lunch (Meals)
|
||||
12:30 - 14:30 Nap Time (Naps)
|
||||
14:30 - 15:00 Snack Time (Meals)
|
||||
15:00 - 15:30 Story Time or Music (varies)
|
||||
15:30 - 16:00 Free Play & Pickup
|
||||
```
|
||||
|
||||
#### Weekly Activity Planning
|
||||
|
||||
**Monday**: Science/Nature focus
|
||||
**Tuesday**: Arts & Crafts day
|
||||
**Wednesday**: Music & Movement
|
||||
**Thursday**: Story & Drama
|
||||
**Friday**: Special Activity & Show & Tell
|
||||
|
||||
### Managing Activity Status
|
||||
|
||||
**Status Options**:
|
||||
|
||||
| Status | Code | Use When |
|
||||
|--------|------|----------|
|
||||
| **Scheduled** | 1 | Activity is planned, not yet completed |
|
||||
| **Completed** | 2 | Activity finished successfully |
|
||||
| **Cancelled** | 0 | Activity didn't happen (weather, etc.) |
|
||||
|
||||
**Updating Status**:
|
||||
1. Go to **Activities → Schedule**
|
||||
2. Find the activity
|
||||
3. Click **Edit**
|
||||
4. Change **Status** to **Completed**
|
||||
5. Add completion notes
|
||||
6. Click **Save**
|
||||
|
||||
### Activity Reports
|
||||
|
||||
View and analyze activities:
|
||||
|
||||
**By Type**: See distribution of activity types
|
||||
**By Date**: View daily/weekly schedules
|
||||
**By Completion**: Track planned vs. completed activities
|
||||
|
||||
---
|
||||
|
||||
## Reports and Analytics
|
||||
|
||||
### Available Reports
|
||||
|
||||
#### Attendance Reports
|
||||
|
||||
**Daily Attendance Report**:
|
||||
- Children present today
|
||||
- Check-in/out times
|
||||
- Daily notes summary
|
||||
- Missing attendance records
|
||||
|
||||
**Monthly Attendance Report**:
|
||||
- Attendance percentage per child
|
||||
- Perfect attendance recognition
|
||||
- Absence patterns
|
||||
- Late arrival/early departure tracking
|
||||
|
||||
**Attendance Trends**:
|
||||
- Busiest days of week
|
||||
- Seasonal attendance patterns
|
||||
- Individual child attendance history
|
||||
|
||||
#### Activity Reports
|
||||
|
||||
**Activity Summary**:
|
||||
- Total activities by type
|
||||
- Completion rate
|
||||
- Most popular activities
|
||||
- Staff activity creation metrics
|
||||
|
||||
**Activity Calendar**:
|
||||
- Visual monthly calendar
|
||||
- Color-coded by activity type
|
||||
- Filter by type or date range
|
||||
|
||||
#### Child Reports
|
||||
|
||||
**Individual Child Report**:
|
||||
- Enrollment information
|
||||
- Attendance summary
|
||||
- Activity participation
|
||||
- Developmental notes
|
||||
- Medical information
|
||||
|
||||
**Enrollment Report**:
|
||||
- Active children count
|
||||
- New enrollments this month/year
|
||||
- Departures/withdrawals
|
||||
- Age distribution
|
||||
- Capacity utilization
|
||||
|
||||
### Generating Reports
|
||||
|
||||
1. Go to **Childcare → Reports**
|
||||
2. Select report type
|
||||
3. Choose date range
|
||||
4. Apply filters (optional)
|
||||
5. Click **Generate**
|
||||
6. View on-screen or download (PDF/Excel)
|
||||
|
||||
### Exporting Data
|
||||
|
||||
Export options for external analysis:
|
||||
- **PDF**: Formatted reports for printing
|
||||
- **Excel**: Raw data for custom analysis
|
||||
- **CSV**: Compatible with most software
|
||||
|
||||
---
|
||||
|
||||
## Daily Workflows
|
||||
|
||||
### Morning Workflow
|
||||
|
||||
**8:00 AM - Opening**:
|
||||
```
|
||||
☐ Review today's activity schedule
|
||||
☐ Check for any special notes (birthdays, events)
|
||||
☐ Prepare attendance list
|
||||
☐ Set up first activity area
|
||||
```
|
||||
|
||||
**8:30 AM - Arrivals Begin**:
|
||||
```
|
||||
☐ Greet each child and parent
|
||||
☐ Record check-in time immediately
|
||||
☐ Note any items brought from home
|
||||
☐ Ask parents about morning routine/concerns
|
||||
☐ Add morning notes to attendance
|
||||
```
|
||||
|
||||
### Midday Workflow
|
||||
|
||||
**Throughout the Day**:
|
||||
```
|
||||
☐ Update attendance notes regularly
|
||||
☐ Mark activities as completed
|
||||
☐ Document incidents immediately
|
||||
☐ Take photos (manual storage for now)
|
||||
☐ Note food intake and nap times
|
||||
```
|
||||
|
||||
**Meal and Activity Transitions**:
|
||||
```
|
||||
☐ Check activity schedule
|
||||
☐ Prepare next activity materials
|
||||
☐ Document current activity completion
|
||||
☐ Transition children smoothly
|
||||
```
|
||||
|
||||
### Afternoon Workflow
|
||||
|
||||
**3:00 PM - Pickup Begins**:
|
||||
```
|
||||
☐ Record check-out times as children leave
|
||||
☐ Complete daily notes for each child
|
||||
☐ Verbally share highlights with parents
|
||||
☐ Send home any artwork or papers
|
||||
☐ Note parent communications needed
|
||||
```
|
||||
|
||||
**5:00 PM - Closing**:
|
||||
```
|
||||
☐ Ensure all check-outs recorded
|
||||
☐ Review day's notes for completeness
|
||||
☐ Prepare tomorrow's schedule
|
||||
☐ Document any concerns for admin
|
||||
☐ Clean up and secure facility
|
||||
```
|
||||
|
||||
### Weekly Workflow
|
||||
|
||||
**Monday**:
|
||||
```
|
||||
☐ Review week's activity plan
|
||||
☐ Check for birthdays or special events
|
||||
☐ Order/prepare materials needed
|
||||
☐ Review last week's attendance
|
||||
```
|
||||
|
||||
**Friday**:
|
||||
```
|
||||
☐ Complete weekly activity report
|
||||
☐ Review attendance for the week
|
||||
☐ Plan next week's activities
|
||||
☐ Send parent communications
|
||||
☐ Organize files and records
|
||||
```
|
||||
|
||||
### Monthly Workflow
|
||||
|
||||
**End of Month**:
|
||||
```
|
||||
☐ Generate monthly attendance report
|
||||
☐ Review activity completion rates
|
||||
☐ Update any medical information
|
||||
☐ Schedule parent conferences if needed
|
||||
☐ Archive completed records
|
||||
☐ Plan next month's special activities
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Tips and Best Practices
|
||||
|
||||
### Data Entry Best Practices
|
||||
|
||||
**Be Consistent**:
|
||||
- Use same time format (24-hour recommended)
|
||||
- Follow naming conventions for references
|
||||
- Complete records same day when possible
|
||||
- Use standard abbreviations
|
||||
|
||||
**Be Thorough**:
|
||||
- Document everything immediately
|
||||
- Include context in notes
|
||||
- Note both positives and concerns
|
||||
- Cross-reference related records
|
||||
|
||||
**Be Accurate**:
|
||||
- Double-check times and dates
|
||||
- Verify child selection in dropdowns
|
||||
- Review before saving
|
||||
- Correct errors immediately
|
||||
|
||||
### Security and Privacy
|
||||
|
||||
**Protecting Child Information**:
|
||||
- ✅ Log out when leaving computer
|
||||
- ✅ Never share login credentials
|
||||
- ✅ Use private notes for sensitive info
|
||||
- ✅ Follow facility privacy policies
|
||||
- ❌ Don't leave screens visible to unauthorized persons
|
||||
- ❌ Don't discuss child info in public areas
|
||||
|
||||
**Access Levels**:
|
||||
- Understand your permission level
|
||||
- Request appropriate access from admin
|
||||
- Report suspicious access attempts
|
||||
- Maintain confidentiality always
|
||||
|
||||
### Communication Tips
|
||||
|
||||
**With Parents**:
|
||||
- Share daily notes verbally at pickup
|
||||
- Highlight positive moments
|
||||
- Address concerns professionally
|
||||
- Document all parent communications
|
||||
- Maintain friendly but professional tone
|
||||
|
||||
**With Staff**:
|
||||
- Share important notes at shift changes
|
||||
- Document handoffs clearly
|
||||
- Alert others to urgent information
|
||||
- Collaborate on activity planning
|
||||
|
||||
### Time Management
|
||||
|
||||
**Efficiency Tips**:
|
||||
1. **Use keyboard shortcuts** when available
|
||||
2. **Batch similar tasks** (all check-ins at once)
|
||||
3. **Prepare templates** for common notes
|
||||
4. **Set reminders** for regular tasks
|
||||
5. **Review dashboard** at start of day
|
||||
|
||||
**Quick Data Entry**:
|
||||
```
|
||||
Instead of: "Emma Johnson arrived at 8:32 AM. She brought her stuffed
|
||||
bear. Mom said she had a good morning."
|
||||
|
||||
Use: "8:32 arrival. Brought bear. Good morning per mom."
|
||||
```
|
||||
|
||||
### Troubleshooting Common Issues
|
||||
|
||||
**Can't Find a Child**:
|
||||
- Check if child status is "Active"
|
||||
- Verify correct spelling
|
||||
- Try searching by reference number
|
||||
- Check if viewing correct entity
|
||||
|
||||
**Time Not Saving**:
|
||||
- Use 24-hour format (HH:MM)
|
||||
- Check timezone settings
|
||||
- Verify time is in valid range
|
||||
- Refresh page and try again
|
||||
|
||||
**Report Not Generating**:
|
||||
- Check date range is valid
|
||||
- Verify you have permission to view reports
|
||||
- Try smaller date range
|
||||
- Contact administrator if persists
|
||||
|
||||
---
|
||||
|
||||
## Keyboard Shortcuts
|
||||
|
||||
| Shortcut | Action |
|
||||
|----------|--------|
|
||||
| `Alt + H` | Go to home/dashboard |
|
||||
| `Alt + N` | New record (context-sensitive) |
|
||||
| `Alt + S` | Save current form |
|
||||
| `Alt + C` | Cancel and return |
|
||||
| `Alt + E` | Edit current record |
|
||||
| `Ctrl + F` | Find/Search |
|
||||
| `Esc` | Close dialog/cancel |
|
||||
|
||||
---
|
||||
|
||||
## Additional Resources
|
||||
|
||||
- 📖 [Quick Start Guide](quick-start.md) - Get started in 10 minutes
|
||||
- 🔧 [Admin Guide](admin-guide.md) - System configuration
|
||||
- 💾 [Database Schema](database-schema.md) - Technical details
|
||||
- 🛠️ [Troubleshooting Guide](troubleshooting.md) - Problem solving
|
||||
|
||||
---
|
||||
|
||||
## Getting Help
|
||||
|
||||
**Questions about using a feature?**
|
||||
- Check this guide first
|
||||
- Ask your facility administrator
|
||||
- Consult Dolibarr documentation
|
||||
|
||||
**Found a bug or issue?**
|
||||
- Document the exact steps to reproduce
|
||||
- Note error messages
|
||||
- Report to your system administrator
|
||||
|
||||
**Need training?**
|
||||
- Ask for hands-on training session
|
||||
- Practice with test data
|
||||
- Review video tutorials (when available)
|
||||
|
||||
---
|
||||
|
||||
**Last Updated**: 2026-02-19
|
||||
**Version**: 1.0.0
|
||||
**For**: MokoDoliCare Childcare Management Module
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCare](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCare) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,647 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliChimp Development Guide
|
||||
|
||||
This comprehensive guide covers the complete development workflow for MokoDoliChimp, with detailed steps for FTP-based development (editing files on remote server) and local development (editing files locally).
|
||||
|
||||
---
|
||||
|
||||
## Table of Contents
|
||||
|
||||
- [Prerequisites](#prerequisites)
|
||||
- [Initial Setup](#initial-setup)
|
||||
- [FTP-Based Development Workflow](#ftp-based-development-workflow)
|
||||
- [Local Development Workflow](#local-development-workflow)
|
||||
- [Common Development Tasks](#common-development-tasks)
|
||||
- [Testing Your Changes](#testing-your-changes)
|
||||
- [Troubleshooting](#troubleshooting)
|
||||
|
||||
---
|
||||
|
||||
## Prerequisites
|
||||
|
||||
### Required Software
|
||||
|
||||
1. **Git** - Version control
|
||||
```bash
|
||||
git --version
|
||||
```
|
||||
|
||||
2. **PHP 7.0+** - For syntax checking
|
||||
```bash
|
||||
php --version
|
||||
```
|
||||
|
||||
3. **Make** - Build automation
|
||||
```bash
|
||||
make --version
|
||||
```
|
||||
|
||||
4. **rsync** - File synchronization (for FTP workflow)
|
||||
```bash
|
||||
rsync --version
|
||||
```
|
||||
|
||||
5. **FTP Client** (Optional - for direct FTP editing)
|
||||
- FileZilla, Cyberduck, or command-line FTP
|
||||
|
||||
### Access Requirements
|
||||
|
||||
- SSH/FTP access to your Dolibarr server
|
||||
- Write permissions to Dolibarr's `htdocs/custom/` directory
|
||||
- Dolibarr admin access for module activation
|
||||
|
||||
---
|
||||
|
||||
## Initial Setup
|
||||
|
||||
### Step 1: Clone the Repository
|
||||
|
||||
Clone the repository with submodules:
|
||||
|
||||
```bash
|
||||
# Navigate to your development directory
|
||||
cd ~/projects
|
||||
|
||||
# Clone with submodules
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliChimp.git
|
||||
|
||||
# Navigate to project directory
|
||||
cd MokoDoliChimp
|
||||
```
|
||||
|
||||
### Step 2: Verify Project Structure
|
||||
|
||||
```bash
|
||||
# Check all required directories exist
|
||||
ls -la
|
||||
|
||||
# Expected output should include:
|
||||
# - src/ (Source code)
|
||||
# - src/admin/ (Admin pages)
|
||||
# - src/class/ (Business logic)
|
||||
# - src/core/ (Module descriptor)
|
||||
# - src/lang/ (Translations)
|
||||
# - docs/ (Documentation)
|
||||
# - scripts/ (Build scripts)
|
||||
# - Makefile (Build automation)
|
||||
```
|
||||
|
||||
### Step 3: Validate Installation
|
||||
|
||||
```bash
|
||||
# Check PHP syntax for all files
|
||||
make check
|
||||
|
||||
# Expected output:
|
||||
# Checking PHP syntax...
|
||||
# ✓ PHP syntax check completed
|
||||
|
||||
# Validate module structure
|
||||
make validate
|
||||
|
||||
# Expected output:
|
||||
# Validating module structure...
|
||||
# ✓ Module structure validated
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## FTP-Based Development Workflow
|
||||
|
||||
This workflow is ideal when you have FTP/SSH access to your Dolibarr server and want to edit files locally, then sync to the server.
|
||||
|
||||
### Overview
|
||||
|
||||
1. Edit files locally on your computer
|
||||
2. Use `make dev-sync` to upload changes to server
|
||||
3. Test changes in Dolibarr
|
||||
4. Repeat as needed
|
||||
|
||||
### Step-by-Step Guide
|
||||
|
||||
#### Step 1: Configure Server Path
|
||||
|
||||
Set your Dolibarr installation path. You have two options:
|
||||
|
||||
**Option A: Set environment variable (recommended)**
|
||||
```bash
|
||||
# Add to your ~/.bashrc or ~/.zshrc for permanent setting
|
||||
export DOLIBARR_PATH=/var/www/html/dolibarr
|
||||
|
||||
# Or set for current session only
|
||||
export DOLIBARR_PATH=/path/to/your/dolibarr
|
||||
```
|
||||
|
||||
**Option B: Specify path with each command**
|
||||
```bash
|
||||
# You'll need to add DOLIBARR_PATH=/path/to/dolibarr to each command
|
||||
make dev-sync DOLIBARR_PATH=/var/www/html/dolibarr
|
||||
```
|
||||
|
||||
#### Step 2: Initial Installation to Server
|
||||
|
||||
First, install the module to your Dolibarr server:
|
||||
|
||||
```bash
|
||||
# If you set DOLIBARR_PATH as environment variable:
|
||||
make install
|
||||
|
||||
# Or specify path directly:
|
||||
make install DOLIBARR_PATH=/var/www/html/dolibarr
|
||||
|
||||
# You may need sudo if the directory requires elevated permissions:
|
||||
sudo make install DOLIBARR_PATH=/var/www/html/dolibarr
|
||||
```
|
||||
|
||||
**Expected Output:**
|
||||
```
|
||||
Installing module to /var/www/html/dolibarr/htdocs/custom/mokodolichimp...
|
||||
Copying module files...
|
||||
Setting permissions...
|
||||
✓ Ownership set to www-data:www-data
|
||||
✓ Module installed to /var/www/html/dolibarr/htdocs/custom/mokodolichimp
|
||||
|
||||
Next steps:
|
||||
1. Go to Dolibarr: Home → Setup → Modules/Applications
|
||||
2. Find 'MokoDoliChimp' and click Activate
|
||||
3. Configure the module settings
|
||||
```
|
||||
|
||||
#### Step 3: Activate Module in Dolibarr
|
||||
|
||||
1. Open your Dolibarr installation in a web browser
|
||||
2. Navigate to: **Home → Setup → Modules/Applications**
|
||||
3. Search for "MokoDoliChimp"
|
||||
4. Click the **Activate** button
|
||||
5. Click the **Settings** button to configure API keys
|
||||
|
||||
#### Step 4: Development Cycle
|
||||
|
||||
Now you're ready to develop! Follow this iterative cycle:
|
||||
|
||||
**A. Edit Files Locally**
|
||||
|
||||
Use your favorite editor to modify files:
|
||||
|
||||
```bash
|
||||
# Example: Edit the main module file
|
||||
code src/mokodolichimp.php
|
||||
|
||||
# Or edit a class file
|
||||
code src/class/mailchimpclient.class.php
|
||||
|
||||
# Or edit the admin page
|
||||
code src/admin/setup.php
|
||||
```
|
||||
|
||||
**B. Validate Changes Locally**
|
||||
|
||||
Before syncing, check for syntax errors:
|
||||
|
||||
```bash
|
||||
# Check PHP syntax
|
||||
make check
|
||||
|
||||
# Expected output:
|
||||
# Checking PHP syntax...
|
||||
# ✓ PHP syntax check completed
|
||||
```
|
||||
|
||||
**C. Sync Changes to Server**
|
||||
|
||||
Upload your changes to the server:
|
||||
|
||||
```bash
|
||||
# Sync files to server
|
||||
make dev-sync
|
||||
|
||||
# Expected output:
|
||||
# Syncing changes to /var/www/html/dolibarr/htdocs/custom/mokodolichimp...
|
||||
# Syncing files from src/ (excluding development artifacts)...
|
||||
# sending incremental file list
|
||||
# mokodolichimp.php
|
||||
# class/mailchimpclient.class.php
|
||||
#
|
||||
# ✓ Files synced successfully
|
||||
# Synced from: /home/user/projects/MokoDoliChimp/src/
|
||||
# Synced to: /var/www/html/dolibarr/htdocs/custom/mokodolichimp
|
||||
```
|
||||
|
||||
**D. Test in Dolibarr**
|
||||
|
||||
1. Refresh your Dolibarr page in the browser
|
||||
2. Test your changes
|
||||
3. Check for errors in Dolibarr's error logs if needed:
|
||||
```bash
|
||||
# On the server
|
||||
tail -f /var/www/html/dolibarr/documents/dolibarr.log
|
||||
```
|
||||
|
||||
**E. Repeat**
|
||||
|
||||
Continue the cycle: Edit → Check → Sync → Test
|
||||
|
||||
### Understanding dev-sync Behavior
|
||||
|
||||
The `make dev-sync` command:
|
||||
|
||||
- **Syncs all module files** from your local directory to server
|
||||
- **Excludes development files** (.git, build artifacts, etc.)
|
||||
- **Uses rsync with --delete** to mirror your local changes exactly
|
||||
- **Creates directory** if it doesn't exist on server
|
||||
- **Preserves permissions** on the server
|
||||
|
||||
**Files that are excluded from sync:**
|
||||
- `.git/` and `.gitignore`
|
||||
- `build/` and `dist/` directories
|
||||
- `Makefile`
|
||||
- `.editorconfig`
|
||||
|
||||
### Step 5: Committing Changes to Git
|
||||
|
||||
After testing and verifying your changes work:
|
||||
|
||||
```bash
|
||||
# Check what files changed
|
||||
git status
|
||||
|
||||
# View specific changes
|
||||
git diff src/mokodolichimp.php
|
||||
|
||||
# Stage your changes
|
||||
git add src/mokodolichimp.php
|
||||
git add src/class/mailchimpclient.class.php
|
||||
|
||||
# Commit with descriptive message
|
||||
git commit -m "feat: add new feature to sync contacts"
|
||||
|
||||
# Push to your branch
|
||||
git push origin your-branch-name
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Local Development Workflow
|
||||
|
||||
This workflow is for local development where Dolibarr runs on the same machine as your development environment.
|
||||
|
||||
### Step 1: Install Dolibarr Locally
|
||||
|
||||
Ensure Dolibarr is installed locally (e.g., via XAMPP, MAMP, or Docker).
|
||||
|
||||
### Step 2: Create Development Symlink
|
||||
|
||||
This creates a symbolic link, so changes in your development directory immediately reflect in Dolibarr:
|
||||
|
||||
```bash
|
||||
# Create symlink
|
||||
sudo make dev-install DOLIBARR_PATH=/path/to/local/dolibarr
|
||||
|
||||
# Expected output:
|
||||
# Creating development symlink...
|
||||
# ✓ Development symlink created
|
||||
# Note: Changes in this directory will be immediately reflected in Dolibarr
|
||||
```
|
||||
|
||||
### Step 3: Activate Module
|
||||
|
||||
Follow the same activation steps as in FTP workflow.
|
||||
|
||||
### Step 4: Development Cycle
|
||||
|
||||
1. **Edit files** in your development directory
|
||||
2. **Changes are immediate** (no sync needed)
|
||||
3. **Refresh browser** to see changes in Dolibarr
|
||||
4. **Test** your changes
|
||||
5. **Commit** when done
|
||||
|
||||
---
|
||||
|
||||
## Common Development Tasks
|
||||
|
||||
### Checking Syntax Before Sync
|
||||
|
||||
Always validate your code before syncing:
|
||||
|
||||
```bash
|
||||
# Check all PHP files
|
||||
make check
|
||||
|
||||
# If there are errors, they'll be shown with line numbers
|
||||
```
|
||||
|
||||
### Building Distribution Package
|
||||
|
||||
Create a ZIP package for distribution:
|
||||
|
||||
```bash
|
||||
# Build package
|
||||
make build
|
||||
|
||||
# Output will be in dist/mokodolichimp-1.0.0.zip
|
||||
ls -lh dist/
|
||||
```
|
||||
|
||||
### Updating Existing Installation
|
||||
|
||||
If you've already installed and want to update:
|
||||
|
||||
```bash
|
||||
# Update installation
|
||||
make update
|
||||
|
||||
# Or for FTP workflow, just use dev-sync:
|
||||
make dev-sync
|
||||
```
|
||||
|
||||
### Cleaning Build Artifacts
|
||||
|
||||
Remove temporary build files:
|
||||
|
||||
```bash
|
||||
# Clean build and dist directories
|
||||
make clean
|
||||
|
||||
# Expected output:
|
||||
# Cleaning build artifacts...
|
||||
# ✓ Clean completed
|
||||
```
|
||||
|
||||
### Viewing All Available Commands
|
||||
|
||||
```bash
|
||||
# Show help
|
||||
make help
|
||||
|
||||
# Output shows all available commands with descriptions
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Testing Your Changes
|
||||
|
||||
### Manual Testing Checklist
|
||||
|
||||
After making changes, test the following:
|
||||
|
||||
1. **Module Activation**
|
||||
- Module appears in Modules/Applications list
|
||||
- Activation completes without errors
|
||||
|
||||
2. **Configuration Page**
|
||||
- Navigate to module settings
|
||||
- All fields display correctly
|
||||
- Can save configuration
|
||||
|
||||
3. **Mailchimp Integration**
|
||||
- API key validation works
|
||||
- Contact sync functionality works
|
||||
- User sync functionality works
|
||||
|
||||
4. **Error Handling**
|
||||
- Invalid API keys show appropriate errors
|
||||
- Network errors are handled gracefully
|
||||
|
||||
### Checking Dolibarr Logs
|
||||
|
||||
```bash
|
||||
# On the server, monitor logs in real-time
|
||||
tail -f /var/www/html/dolibarr/documents/dolibarr.log
|
||||
|
||||
# Or check recent errors
|
||||
tail -50 /var/www/html/dolibarr/documents/dolibarr.log | grep ERROR
|
||||
```
|
||||
|
||||
### PHP Error Logs
|
||||
|
||||
```bash
|
||||
# Check Apache error logs (Ubuntu/Debian)
|
||||
sudo tail -f /var/log/apache2/error.log
|
||||
|
||||
# Check PHP-FPM logs (if using PHP-FPM)
|
||||
sudo tail -f /var/log/php-fpm/error.log
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Issue: "make: command not found"
|
||||
|
||||
**Solution:** Install make utility
|
||||
|
||||
```bash
|
||||
# Ubuntu/Debian
|
||||
sudo apt-get install make
|
||||
|
||||
# macOS (via Homebrew)
|
||||
brew install make
|
||||
|
||||
# CentOS/RHEL
|
||||
sudo yum install make
|
||||
```
|
||||
|
||||
### Issue: "rsync: command not found"
|
||||
|
||||
**Solution:** Install rsync
|
||||
|
||||
```bash
|
||||
# Ubuntu/Debian
|
||||
sudo apt-get install rsync
|
||||
|
||||
# macOS (usually pre-installed, but if needed)
|
||||
brew install rsync
|
||||
|
||||
# CentOS/RHEL
|
||||
sudo yum install rsync
|
||||
```
|
||||
|
||||
### Issue: Permission Denied When Syncing
|
||||
|
||||
**Solution:** Use sudo or fix permissions
|
||||
|
||||
```bash
|
||||
# Option 1: Use sudo
|
||||
sudo make dev-sync
|
||||
|
||||
# Option 2: Fix directory permissions (on server)
|
||||
sudo chown -R $USER:www-data /var/www/html/dolibarr/htdocs/custom
|
||||
sudo chmod -R 775 /var/www/html/dolibarr/htdocs/custom
|
||||
```
|
||||
|
||||
### Issue: Module Not Appearing in Dolibarr
|
||||
|
||||
**Checklist:**
|
||||
|
||||
1. Verify files are in correct directory:
|
||||
```bash
|
||||
ls -la /var/www/html/dolibarr/htdocs/custom/mokodolichimp/
|
||||
```
|
||||
|
||||
2. Check file permissions:
|
||||
```bash
|
||||
ls -la /var/www/html/dolibarr/htdocs/custom/mokodolichimp/*.php
|
||||
# Files should be readable by web server (644 or 755)
|
||||
```
|
||||
|
||||
3. Check Dolibarr module cache:
|
||||
- In Dolibarr, go to: Home → Setup → Other
|
||||
- Clear all caches
|
||||
- Refresh the Modules/Applications page
|
||||
|
||||
4. Check for PHP errors:
|
||||
```bash
|
||||
tail -f /var/www/html/dolibarr/documents/dolibarr.log
|
||||
```
|
||||
|
||||
### Issue: Changes Not Reflected After Sync
|
||||
|
||||
**Solutions:**
|
||||
|
||||
1. **Clear browser cache:** Use Ctrl+F5 (Windows/Linux) or Cmd+Shift+R (Mac)
|
||||
|
||||
2. **Clear Dolibarr cache:**
|
||||
- Home → Setup → Other → "Clear all cache"
|
||||
|
||||
3. **Verify sync completed:**
|
||||
```bash
|
||||
# Check file timestamps on server
|
||||
ls -lat /var/www/html/dolibarr/htdocs/custom/mokodolichimp/ | head -10
|
||||
```
|
||||
|
||||
4. **Force full sync:**
|
||||
```bash
|
||||
# Remove module directory and re-sync
|
||||
sudo rm -rf /var/www/html/dolibarr/htdocs/custom/mokodolichimp
|
||||
sudo make dev-sync
|
||||
```
|
||||
|
||||
### Issue: PHP Syntax Errors
|
||||
|
||||
**Solution:** Run syntax check and fix errors
|
||||
|
||||
```bash
|
||||
# Check syntax
|
||||
make check
|
||||
|
||||
# Fix the reported errors
|
||||
# Then re-sync
|
||||
make dev-sync
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Always Check Syntax Before Syncing
|
||||
|
||||
```bash
|
||||
make check && make dev-sync
|
||||
```
|
||||
|
||||
### 2. Use Version Control Branches
|
||||
|
||||
```bash
|
||||
# Create feature branch
|
||||
git checkout -b feature/my-new-feature
|
||||
|
||||
# Make changes, sync, test
|
||||
# ...
|
||||
|
||||
# Commit and push
|
||||
git add .
|
||||
git commit -m "feat: add my new feature"
|
||||
git push origin feature/my-new-feature
|
||||
```
|
||||
|
||||
### 3. Test in Staging Before Production
|
||||
|
||||
- Use a separate Dolibarr staging instance
|
||||
- Test all changes thoroughly
|
||||
- Only deploy to production after validation
|
||||
|
||||
### 4. Keep Development Environment Updated
|
||||
|
||||
```bash
|
||||
# Pull latest changes
|
||||
git pull origin main
|
||||
|
||||
# Update submodules
|
||||
git submodule update --remote
|
||||
|
||||
# Re-sync to server
|
||||
make dev-sync
|
||||
```
|
||||
|
||||
### 5. Document Your Changes
|
||||
|
||||
- Update CHANGELOG.md for significant changes
|
||||
- Add comments to complex code
|
||||
- Update README.md if adding new features
|
||||
|
||||
---
|
||||
|
||||
## Quick Reference
|
||||
|
||||
### Common Commands
|
||||
|
||||
```bash
|
||||
# Initial setup
|
||||
git clone --recurse-submodules https://github.com/mokoconsulting-tech/MokoDoliChimp.git
|
||||
cd MokoDoliChimp
|
||||
|
||||
# Set Dolibarr path (add to ~/.bashrc for permanence)
|
||||
export DOLIBARR_PATH=/var/www/html/dolibarr
|
||||
|
||||
# Validate code
|
||||
make check
|
||||
|
||||
# Sync to server (FTP workflow)
|
||||
make dev-sync
|
||||
|
||||
# Create symlink (Local workflow)
|
||||
sudo make dev-install
|
||||
|
||||
# Build distribution
|
||||
make build
|
||||
|
||||
# Show all commands
|
||||
make help
|
||||
```
|
||||
|
||||
### File Locations
|
||||
|
||||
- **Module files on server:** `/var/www/html/dolibarr/htdocs/custom/mokodolichimp/`
|
||||
- **Dolibarr logs:** `/var/www/html/dolibarr/documents/dolibarr.log`
|
||||
- **Apache logs:** `/var/log/apache2/error.log`
|
||||
- **Distribution packages:** `./dist/mokodolichimp-1.0.0.zip`
|
||||
|
||||
### Key Files to Edit
|
||||
|
||||
- **Main module file:** `src/mokodolichimp.php`
|
||||
- **Module descriptor:** `src/core/modules/modMokoDoliChimp.class.php`
|
||||
- **Mailchimp client:** `src/class/mailchimpclient.class.php`
|
||||
- **Hook actions:** `src/class/actions_mokodolichimp.class.php`
|
||||
- **Admin setup page:** `src/admin/setup.php`
|
||||
- **Translations:** `src/lang/en_US/mokodolichimp.lang`
|
||||
|
||||
---
|
||||
|
||||
## Getting Help
|
||||
|
||||
- **Issues:** https://github.com/mokoconsulting-tech/MokoDoliChimp/issues
|
||||
- **moko-platform:** https://github.com/mokoconsulting-tech/moko-platform
|
||||
- **Dolibarr Wiki:** https://wiki.dolibarr.org/
|
||||
|
||||
---
|
||||
|
||||
**Happy Coding! 🚀**
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliChimp](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliChimp) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,26 @@
|
||||
# MokoDoliChimp
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliChimp) |
|
||||
|
||||
---
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [DEVELOPMENT_GUIDE](DEVELOPMENT_GUIDE) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliChimp](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliChimp) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,43 @@
|
||||
# MokoDoliClaude
|
||||
|
||||
A connector for Dolibarr and Claude
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,148 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Documentation Index
|
||||
|
||||
Welcome to the moko-platform Dolibarr Template documentation. This guide will help you navigate all available documentation resources.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Get started with installing the template
|
||||
- [Development Guide](development.md) - Learn how to develop Dolibarr modules
|
||||
- [Module ID Policy](module-id-policy.md) - Understand module ID assignment process
|
||||
- [Changelog](changelog.md) - Track version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For New Users
|
||||
|
||||
If you're new to this template, start here:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Configuration and setup
|
||||
- Troubleshooting common issues
|
||||
|
||||
2. **[Module ID Policy](module-id-policy.md)**
|
||||
- Understanding module IDs
|
||||
- Development vs. production IDs
|
||||
- How to request an official ID
|
||||
- Best practices
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're developing a module, these guides will help:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and organization
|
||||
- Module descriptor configuration
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
2. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Code standards
|
||||
- Pull request process
|
||||
- Commit message guidelines
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Installation Guide](installation.md) to set up the template, then review the [Development Guide](development.md) for building your module.
|
||||
|
||||
**Q: What module ID should I use?**
|
||||
A: Use an ID greater than 600,000 during development. See the [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
**Q: Where are the code examples?**
|
||||
A: The [Development Guide](development.md) contains numerous code examples and best practices.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
|
||||
### moko-platform
|
||||
|
||||
- [MokoConsulting Tech GitHub](https://github.com/mokoconsulting-tech)
|
||||
- Template Repository: [moko-platform-Template-Dolibarr](https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 600001; // Development module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/
|
||||
git clone repo-url
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Template Version**: 1.0.0
|
||||
- **Last Updated**: 2026-01-16
|
||||
- **Minimum Dolibarr Version**: 12.0
|
||||
- **PHP Version**: 7.4+
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- New to the template? Start with [Installation Guide](installation.md)
|
||||
- Ready to develop? Check out [Development Guide](development.md)
|
||||
- Need to request a module ID? Review [Module ID Policy](module-id-policy.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,70 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to this project template will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Added
|
||||
- Comprehensive README.md with project overview and usage instructions
|
||||
- Module ID policy documentation
|
||||
- Installation guide with detailed setup instructions
|
||||
- Development guide with best practices and examples
|
||||
- Contributing guidelines
|
||||
- Documentation structure following moko-platform
|
||||
|
||||
## [1.0.0] - 2026-01-16
|
||||
|
||||
### Added
|
||||
- Initial template structure for Dolibarr modules
|
||||
- Basic documentation framework
|
||||
- Module ID policy requiring issue-based requests
|
||||
- Support for temporary development IDs (600,000+)
|
||||
|
||||
---
|
||||
|
||||
## Template Usage Notes
|
||||
|
||||
When using this template for your module:
|
||||
|
||||
1. Copy this changelog to your project
|
||||
2. Update the version numbers as you develop
|
||||
3. Document all changes in the appropriate category:
|
||||
- **Added** for new features
|
||||
- **Changed** for changes in existing functionality
|
||||
- **Deprecated** for soon-to-be removed features
|
||||
- **Removed** for now removed features
|
||||
- **Fixed** for any bug fixes
|
||||
- **Security** for vulnerability fixes
|
||||
|
||||
Example entry:
|
||||
```markdown
|
||||
## [1.1.0] - 2026-02-15
|
||||
|
||||
### Added
|
||||
- New feature X for handling Y
|
||||
- Support for Z functionality
|
||||
|
||||
### Fixed
|
||||
- Bug in module activation
|
||||
- Permission check in admin page
|
||||
|
||||
### Changed
|
||||
- Updated module descriptor format
|
||||
- Improved error handling
|
||||
```
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/compare/v1.0.0...HEAD
|
||||
[1.0.0]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/releases/tag/v1.0.0
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,323 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - use 600,000+ for development
|
||||
$this->numero = 600001;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Development Phase
|
||||
|
||||
Use module ID > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,173 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring your Dolibarr module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 12.0 or higher
|
||||
- **PHP**: Version 7.4 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- gd or imagick
|
||||
- curl
|
||||
- json
|
||||
- xml
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr's custom directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone this template repository:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr.git yourmodule
|
||||
```
|
||||
|
||||
Replace `yourmodule` with your desired module name (lowercase, no spaces).
|
||||
|
||||
### 2. Rename and Configure
|
||||
|
||||
Navigate to the module directory:
|
||||
|
||||
```bash
|
||||
cd yourmodule
|
||||
```
|
||||
|
||||
Rename the module descriptor file:
|
||||
|
||||
```bash
|
||||
mv modYourmodule.class.php modYourModuleName.class.php
|
||||
```
|
||||
|
||||
### 3. Configure Module ID
|
||||
|
||||
Open the module descriptor file and set a temporary module ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourModuleName.class.php
|
||||
$this->numero = 600001; // Use a number > 600,000 for development
|
||||
```
|
||||
|
||||
**Important:** Before publishing, request an official module ID by creating an issue in the repository.
|
||||
|
||||
### 4. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 5. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find your module in the list
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 6. Configure Module Settings (if applicable)
|
||||
|
||||
After activation:
|
||||
|
||||
1. Go to **Home → Setup → Modules/Applications**
|
||||
2. Click on your module name to access its configuration page
|
||||
3. Configure any required settings
|
||||
4. Save changes
|
||||
|
||||
## Database Setup
|
||||
|
||||
If your module requires database tables:
|
||||
|
||||
### Automatic Setup
|
||||
|
||||
The module descriptor can handle automatic table creation during activation. Ensure your SQL files are in the `sql/` directory:
|
||||
|
||||
```
|
||||
sql/
|
||||
├── llx_yourmodule_table.sql
|
||||
└── llx_yourmodule_table.key.sql
|
||||
```
|
||||
|
||||
### Manual Setup
|
||||
|
||||
Alternatively, run SQL scripts manually:
|
||||
|
||||
```bash
|
||||
mysql -u username -p database_name < sql/llx_yourmodule_table.sql
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Clear Dolibarr cache: Delete `/documents/install.lock` and refresh
|
||||
- Check file permissions
|
||||
- Verify PHP syntax errors: `php -l modYourModuleName.class.php`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure Apache/Nginx user has read access to all module files
|
||||
- Check `conf.php` file permissions in Dolibarr root
|
||||
|
||||
### Database Errors
|
||||
|
||||
- Verify database credentials in Dolibarr's `conf/conf.php`
|
||||
- Check SQL file syntax
|
||||
- Ensure database user has CREATE TABLE permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find your module and click **Deactivate**
|
||||
3. Optionally, remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
```
|
||||
|
||||
**Note:** Deactivating the module does not remove database tables. To remove data:
|
||||
|
||||
```sql
|
||||
DROP TABLE llx_yourmodule_table;
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Review the [Development Guide](development.md) to start customizing your module
|
||||
- Check the [Module ID Policy](module-id-policy.md) before distribution
|
||||
- Read the [Changelog](changelog.md) for version history
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Create an issue in the repository
|
||||
- Check Dolibarr logs: `/documents/dolibarr.log`
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliClaude/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliClaude](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliClaude) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,41 @@
|
||||
# MokoDoliCredits
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,148 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Documentation Index
|
||||
|
||||
Welcome to the moko-platform Dolibarr Template documentation. This guide will help you navigate all available documentation resources.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Get started with installing the template
|
||||
- [Development Guide](development.md) - Learn how to develop Dolibarr modules
|
||||
- [Module ID Policy](module-id-policy.md) - Understand module ID assignment process
|
||||
- [Changelog](changelog.md) - Track version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For New Users
|
||||
|
||||
If you're new to this template, start here:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Configuration and setup
|
||||
- Troubleshooting common issues
|
||||
|
||||
2. **[Module ID Policy](module-id-policy.md)**
|
||||
- Understanding module IDs
|
||||
- Development vs. production IDs
|
||||
- How to request an official ID
|
||||
- Best practices
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're developing a module, these guides will help:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and organization
|
||||
- Module descriptor configuration
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
2. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Code standards
|
||||
- Pull request process
|
||||
- Commit message guidelines
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Installation Guide](installation.md) to set up the template, then review the [Development Guide](development.md) for building your module.
|
||||
|
||||
**Q: What module ID should I use?**
|
||||
A: Use an ID greater than 600,000 during development. See the [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
**Q: Where are the code examples?**
|
||||
A: The [Development Guide](development.md) contains numerous code examples and best practices.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
|
||||
### moko-platform
|
||||
|
||||
- [MokoConsulting Tech GitHub](https://github.com/mokoconsulting-tech)
|
||||
- Template Repository: [moko-platform-Template-Dolibarr](https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 600001; // Development module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/
|
||||
git clone repo-url
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Template Version**: 1.0.0
|
||||
- **Last Updated**: 2026-01-16
|
||||
- **Minimum Dolibarr Version**: 12.0
|
||||
- **PHP Version**: 7.4+
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- New to the template? Start with [Installation Guide](installation.md)
|
||||
- Ready to develop? Check out [Development Guide](development.md)
|
||||
- Need to request a module ID? Review [Module ID Policy](module-id-policy.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,70 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to this project template will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Added
|
||||
- Comprehensive README.md with project overview and usage instructions
|
||||
- Module ID policy documentation
|
||||
- Installation guide with detailed setup instructions
|
||||
- Development guide with best practices and examples
|
||||
- Contributing guidelines
|
||||
- Documentation structure following moko-platform
|
||||
|
||||
## [1.0.0] - 2026-01-16
|
||||
|
||||
### Added
|
||||
- Initial template structure for Dolibarr modules
|
||||
- Basic documentation framework
|
||||
- Module ID policy requiring issue-based requests
|
||||
- Support for temporary development IDs (600,000+)
|
||||
|
||||
---
|
||||
|
||||
## Template Usage Notes
|
||||
|
||||
When using this template for your module:
|
||||
|
||||
1. Copy this changelog to your project
|
||||
2. Update the version numbers as you develop
|
||||
3. Document all changes in the appropriate category:
|
||||
- **Added** for new features
|
||||
- **Changed** for changes in existing functionality
|
||||
- **Deprecated** for soon-to-be removed features
|
||||
- **Removed** for now removed features
|
||||
- **Fixed** for any bug fixes
|
||||
- **Security** for vulnerability fixes
|
||||
|
||||
Example entry:
|
||||
```markdown
|
||||
## [1.1.0] - 2026-02-15
|
||||
|
||||
### Added
|
||||
- New feature X for handling Y
|
||||
- Support for Z functionality
|
||||
|
||||
### Fixed
|
||||
- Bug in module activation
|
||||
- Permission check in admin page
|
||||
|
||||
### Changed
|
||||
- Updated module descriptor format
|
||||
- Improved error handling
|
||||
```
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/compare/v1.0.0...HEAD
|
||||
[1.0.0]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/releases/tag/v1.0.0
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,323 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - use 600,000+ for development
|
||||
$this->numero = 600001;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Development Phase
|
||||
|
||||
Use module ID > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,173 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring your Dolibarr module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 12.0 or higher
|
||||
- **PHP**: Version 7.4 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- gd or imagick
|
||||
- curl
|
||||
- json
|
||||
- xml
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr's custom directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone this template repository:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr.git yourmodule
|
||||
```
|
||||
|
||||
Replace `yourmodule` with your desired module name (lowercase, no spaces).
|
||||
|
||||
### 2. Rename and Configure
|
||||
|
||||
Navigate to the module directory:
|
||||
|
||||
```bash
|
||||
cd yourmodule
|
||||
```
|
||||
|
||||
Rename the module descriptor file:
|
||||
|
||||
```bash
|
||||
mv modYourmodule.class.php modYourModuleName.class.php
|
||||
```
|
||||
|
||||
### 3. Configure Module ID
|
||||
|
||||
Open the module descriptor file and set a temporary module ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourModuleName.class.php
|
||||
$this->numero = 600001; // Use a number > 600,000 for development
|
||||
```
|
||||
|
||||
**Important:** Before publishing, request an official module ID by creating an issue in the repository.
|
||||
|
||||
### 4. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 5. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find your module in the list
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 6. Configure Module Settings (if applicable)
|
||||
|
||||
After activation:
|
||||
|
||||
1. Go to **Home → Setup → Modules/Applications**
|
||||
2. Click on your module name to access its configuration page
|
||||
3. Configure any required settings
|
||||
4. Save changes
|
||||
|
||||
## Database Setup
|
||||
|
||||
If your module requires database tables:
|
||||
|
||||
### Automatic Setup
|
||||
|
||||
The module descriptor can handle automatic table creation during activation. Ensure your SQL files are in the `sql/` directory:
|
||||
|
||||
```
|
||||
sql/
|
||||
├── llx_yourmodule_table.sql
|
||||
└── llx_yourmodule_table.key.sql
|
||||
```
|
||||
|
||||
### Manual Setup
|
||||
|
||||
Alternatively, run SQL scripts manually:
|
||||
|
||||
```bash
|
||||
mysql -u username -p database_name < sql/llx_yourmodule_table.sql
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Clear Dolibarr cache: Delete `/documents/install.lock` and refresh
|
||||
- Check file permissions
|
||||
- Verify PHP syntax errors: `php -l modYourModuleName.class.php`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure Apache/Nginx user has read access to all module files
|
||||
- Check `conf.php` file permissions in Dolibarr root
|
||||
|
||||
### Database Errors
|
||||
|
||||
- Verify database credentials in Dolibarr's `conf/conf.php`
|
||||
- Check SQL file syntax
|
||||
- Ensure database user has CREATE TABLE permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find your module and click **Deactivate**
|
||||
3. Optionally, remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
```
|
||||
|
||||
**Note:** Deactivating the module does not remove database tables. To remove data:
|
||||
|
||||
```sql
|
||||
DROP TABLE llx_yourmodule_table;
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Review the [Development Guide](development.md) to start customizing your module
|
||||
- Check the [Module ID Policy](module-id-policy.md) before distribution
|
||||
- Read the [Changelog](changelog.md) for version history
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Create an issue in the repository
|
||||
- Check Dolibarr logs: `/documents/dolibarr.log`
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliCredits/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliCredits](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliCredits) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,43 @@
|
||||
# MokoDoliDymo
|
||||
|
||||
A module to design label documents for Dymo LabelWriter
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
| [dymo label format](dymo-label-format.-.-) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,39 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliDymo Documentation
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) — Setup and configuration
|
||||
- [Development Guide](development.md) — Architecture, coding standards, extending the module
|
||||
- [Changelog](changelog.md) — Version history
|
||||
|
||||
## For Users
|
||||
|
||||
Start with the [Installation Guide](installation.md) to get MokoDoliDymo running on your Dolibarr instance. Once installed, the module adds a **MokoDoliDymo** entry to the top menu where you can design and manage label templates.
|
||||
|
||||
## For Developers
|
||||
|
||||
The [Development Guide](development.md) covers the module architecture, how to add new label field types, and how to extend data binding to additional Dolibarr objects.
|
||||
|
||||
This module follows [moko-platform](https://github.com/mokoconsulting-tech/moko-platform) conventions. See the [Contributing Guidelines](CONTRIBUTING) for PR and coding requirements.
|
||||
|
||||
## Resources
|
||||
|
||||
- [moko-platform](https://github.com/mokoconsulting-tech/moko-platform) — Governance and coding standards
|
||||
- [MokoDoliDymo Repository](https://github.com/mokoconsulting-tech/MokoDoliDymo)
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
|
||||
## Module Info
|
||||
|
||||
- **Module ID**: 185072
|
||||
- **Minimum Dolibarr**: 19.0
|
||||
- **PHP**: 8.1+
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,33 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to MokoDoliDymo will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
## [01.00.00] - 2026-03-31
|
||||
|
||||
### Added
|
||||
|
||||
- Initial module scaffolding for MokoDoliDymo
|
||||
- Module descriptor with ID 185072
|
||||
- Admin setup and about pages
|
||||
- Language file with label designer translations
|
||||
- Permissions: label read, write, delete, print
|
||||
- Top menu entry for MokoDoliDymo
|
||||
- Documentation: installation guide, development guide, changelog
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/MokoDoliDymo/compare/v01.00.00...HEAD
|
||||
[01.00.00]: https://github.com/mokoconsulting-tech/MokoDoliDymo/releases/tag/v01.00.00
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,142 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide covers developing and extending MokoDoliDymo.
|
||||
|
||||
## Module Structure
|
||||
|
||||
```
|
||||
mokodolidymo/
|
||||
├── core/
|
||||
│ └── modules/
|
||||
│ └── modMokoDoliDymo.class.php # Module descriptor (ID 185072)
|
||||
├── class/ # Business logic classes
|
||||
├── langs/
|
||||
│ └── en_US/
|
||||
│ └── mokodolidymo.lang # Translations
|
||||
├── sql/ # Database schema
|
||||
├── lib/
|
||||
│ └── mokodolidymo.lib.php # Shared library functions
|
||||
├── admin/
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── img/ # Icons and images
|
||||
└── mokodolidymoindex.php # Module home page
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor at `core/modules/modMokoDoliDymo.class.php` defines:
|
||||
|
||||
- **Module ID**: `185072` — permanently registered, never change
|
||||
- **Rights class**: `mokodolidymo`
|
||||
- **Permissions**: `label.read`, `label.write`, `label.delete`, `label.print`
|
||||
- **Version**: Must match `README.md`
|
||||
|
||||
## Coding Standards
|
||||
|
||||
This project follows [moko-platform](https://github.com/mokoconsulting-tech/moko-platform):
|
||||
|
||||
| Context | Convention |
|
||||
|---------|-----------|
|
||||
| PHP class | `PascalCase` |
|
||||
| PHP method | `camelCase` |
|
||||
| PHP variable | `$snake_case` |
|
||||
| PHP constant | `UPPER_SNAKE_CASE` |
|
||||
| Indentation | Tabs (per `.editorconfig`) |
|
||||
|
||||
### Security
|
||||
|
||||
```php
|
||||
// Always check permissions
|
||||
if (!$user->hasRight('mokodolidymo', 'label', 'read')) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOSTINT('id');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
### Translations
|
||||
|
||||
Add keys to `langs/en_US/mokodolidymo.lang`:
|
||||
|
||||
```
|
||||
MyNewKey = My translated string
|
||||
```
|
||||
|
||||
Use in PHP:
|
||||
|
||||
```php
|
||||
$langs->load("mokodolidymo@mokodolidymo");
|
||||
print $langs->trans("MyNewKey");
|
||||
```
|
||||
|
||||
### Database
|
||||
|
||||
SQL files go in `sql/` and are auto-loaded on module activation:
|
||||
|
||||
```
|
||||
sql/
|
||||
├── llx_mokodolidymo_label.sql
|
||||
└── llx_mokodolidymo_label.key.sql
|
||||
```
|
||||
|
||||
## Version Management
|
||||
|
||||
- **`README.md`** is the single source of truth for the version
|
||||
- `$this->version` in the module descriptor must always match
|
||||
- Bump patch version on every PR (`01.00.00` -> `01.00.01`)
|
||||
- Format: zero-padded semver `XX.YY.ZZ`
|
||||
|
||||
## File Headers
|
||||
|
||||
Every new PHP file requires a copyright header:
|
||||
|
||||
```php
|
||||
<?php
|
||||
/* Copyright (C) 2026 Moko Consulting <hello@mokoconsulting.tech>
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-3.0-or-later
|
||||
*
|
||||
* FILE INFORMATION
|
||||
* DEFGROUP: MokoDoliDymo.Module
|
||||
* INGROUP: MokoDoliDymo
|
||||
* REPO: https://github.com/mokoconsulting-tech/MokoDoliDymo
|
||||
* PATH: /src/class/MyClass.php
|
||||
* VERSION: 01.00.00
|
||||
* BRIEF: One-line description
|
||||
*/
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
```bash
|
||||
# Run PHP linting
|
||||
php -l src/core/modules/modMokoDoliDymo.class.php
|
||||
|
||||
# Run PHPStan
|
||||
composer phpstan
|
||||
|
||||
# Run code style checks
|
||||
composer phpcs
|
||||
```
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [moko-platform](https://github.com/mokoconsulting-tech/moko-platform)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,162 @@
|
||||
← [Home](Home)
|
||||
|
||||
# DYMO Label File Format
|
||||
|
||||
This document describes the DYMO Desktop Label XML format (`.dymo` / `.label` files) used by DYMO Connect and DYMO Label software. MokoDoliDymo can import these files as label template starting points.
|
||||
|
||||
## File Structure
|
||||
|
||||
DYMO label files are XML with the root element `<DesktopLabel Version="1">`.
|
||||
|
||||
```xml
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<DesktopLabel Version="1">
|
||||
<DYMOLabel Version="4">
|
||||
</DYMOLabel>
|
||||
<LabelApplication>Blank</LabelApplication>
|
||||
<DataTable>
|
||||
<Columns></Columns>
|
||||
<Rows></Rows>
|
||||
</DataTable>
|
||||
</DesktopLabel>
|
||||
```
|
||||
|
||||
## Key Elements
|
||||
|
||||
### DYMOLabel
|
||||
|
||||
The main label definition container.
|
||||
|
||||
| Element | Description |
|
||||
|---------|-------------|
|
||||
| `Description` | Human-readable label description |
|
||||
| `Orientation` | `Landscape` or `Portrait` |
|
||||
| `LabelName` | DYMO label stock name (e.g. `Address30251`, `Shipping30256`) |
|
||||
| `DYMORect` | Label printable area rectangle |
|
||||
| `DynamicLayoutManager > LabelObjects` | Container for all label elements |
|
||||
|
||||
### DYMORect / ObjectLayout — Coordinates
|
||||
|
||||
All coordinates and sizes are in **inches**. Each object has an `ObjectLayout` block:
|
||||
|
||||
```xml
|
||||
<ObjectLayout>
|
||||
<DYMOPoint>
|
||||
</DYMOPoint>
|
||||
<Size>
|
||||
</Size>
|
||||
</ObjectLayout>
|
||||
```
|
||||
|
||||
**Conversion**: 1 inch = 25.4 mm
|
||||
|
||||
The label's printable area is defined by `DYMORect` with the same `DYMOPoint` + `Size` structure.
|
||||
|
||||
### Label Objects
|
||||
|
||||
Objects live inside `DynamicLayoutManager > LabelObjects`. Supported types:
|
||||
|
||||
#### TextObject
|
||||
|
||||
```xml
|
||||
<TextObject>
|
||||
<Name>TextObject0</Name>
|
||||
<FormattedText>
|
||||
<LineTextSpan>
|
||||
<TextSpan>
|
||||
<Text>Hello World</Text>
|
||||
<FontInfo>
|
||||
<FontName>Segoe UI</FontName>
|
||||
<FontSize>26.9</FontSize>
|
||||
<IsBold>False</IsBold>
|
||||
<IsItalic>False</IsItalic>
|
||||
<IsUnderline>False</IsUnderline>
|
||||
</FontInfo>
|
||||
</TextSpan>
|
||||
</LineTextSpan>
|
||||
</FormattedText>
|
||||
<ObjectLayout>...</ObjectLayout>
|
||||
</TextObject>
|
||||
```
|
||||
|
||||
#### BarcodeObject
|
||||
|
||||
```xml
|
||||
<BarcodeObject>
|
||||
<Name>BarcodeObject0</Name>
|
||||
<Text>123456789</Text>
|
||||
<ObjectLayout>...</ObjectLayout>
|
||||
</BarcodeObject>
|
||||
```
|
||||
|
||||
Common barcode formats: `Code128Auto`, `QRCode`, `EAN13`, `EAN8`, `UPCA`, `Code39`, `ITF14`, `PDF417`, `DataMatrix`
|
||||
|
||||
#### ImageObject
|
||||
|
||||
```xml
|
||||
<ImageObject>
|
||||
<Name>ImageObject0</Name>
|
||||
<ObjectLayout>...</ObjectLayout>
|
||||
</ImageObject>
|
||||
```
|
||||
|
||||
#### ShapeObject
|
||||
|
||||
```xml
|
||||
<ShapeObject>
|
||||
<Name>ShapeObject0</Name>
|
||||
<ObjectLayout>...</ObjectLayout>
|
||||
</ShapeObject>
|
||||
```
|
||||
|
||||
### Common Properties
|
||||
|
||||
All label objects share these:
|
||||
|
||||
| Property | Values | Description |
|
||||
|----------|--------|-------------|
|
||||
| `Rotation` | `Rotation0`, `Rotation90`, `Rotation180`, `Rotation270` | Element rotation |
|
||||
| `Brushes` | Complex | Fill, border, stroke, and background colors |
|
||||
| `Margin` | `DYMOThickness Left/Top/Right/Bottom` | Inner padding (inches) |
|
||||
| `BorderStyle` | `SolidLine`, `None` | Border drawing style |
|
||||
| `OutlineThickness` | Float | Outline stroke width |
|
||||
|
||||
### Label Stock Names
|
||||
|
||||
The `LabelName` field identifies the DYMO label roll. Common values:
|
||||
|
||||
| LabelName | DYMO Part# | Size (inches) | Size (mm) |
|
||||
|-----------|-----------|---------------|-----------|
|
||||
| `Address30251` | 30251 | 1-1/8 x 3-1/2 | 28.6 x 88.9 |
|
||||
| `Address30252` | 30252 | 1-1/8 x 3-1/2 | 28.6 x 88.9 |
|
||||
| `Shipping30256` | 30256 | 2-5/16 x 4 | 58.7 x 101.6 |
|
||||
| `ReturnAddress30330` | 30330 | 3/4 x 2 | 19.1 x 50.8 |
|
||||
| `MultiPurpose30334` | 30334 | 1 x 2-1/8 | 25.4 x 57.2 |
|
||||
| `FileFolder30327` | 30327 | 9/16 x 3-7/16 | 14.3 x 87.3 |
|
||||
| `NameBadge30857` | 30857 | 2-1/4 x 4 | 57.2 x 101.6 |
|
||||
|
||||
## MokoDoliDymo Import Behavior
|
||||
|
||||
When importing a `.dymo` or `.label` file:
|
||||
|
||||
1. The XML is parsed to extract the label dimensions from `DYMORect`
|
||||
2. Each `LabelObject` is converted to a MokoDoliDymo layout element
|
||||
3. Coordinates are converted from inches to millimeters (multiply by 25.4)
|
||||
4. Font sizes and text properties are preserved where possible
|
||||
5. Barcode types are mapped to Dolibarr-compatible formats
|
||||
6. Image data is extracted and stored separately
|
||||
7. The resulting JSON layout can be further edited in the visual designer
|
||||
|
||||
## References
|
||||
|
||||
- [DYMO Developer SDK](https://developers.dymo.com/)
|
||||
- [DYMO Connect JavaScript Framework](https://developers.dymo.com/tag/javascript/)
|
||||
- [DYMO Label Framework Technical Reference](https://developers.dymo.com/2010/06/02/dymo-label-framework-javascript-library-samples-and-docs/)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,90 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
## Prerequisites
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 19.0 or higher
|
||||
- **PHP**: 8.1 or higher
|
||||
- **DYMO LabelWriter**: LabelWriter 450, 550, or compatible model
|
||||
- **PHP Extensions**: mysqli or pgsql, gd, curl, json
|
||||
|
||||
## Installation
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr custom modules directory and clone:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
git clone https://github.com/mokoconsulting-tech/MokoDoliDymo.git mokodolidymo
|
||||
```
|
||||
|
||||
### 2. Set File Permissions
|
||||
|
||||
```bash
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/mokodolidymo
|
||||
find /path/to/dolibarr/htdocs/custom/mokodolidymo -type d -exec chmod 755 {} \;
|
||||
find /path/to/dolibarr/htdocs/custom/mokodolidymo -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 3. Enable the Module
|
||||
|
||||
1. Log in to Dolibarr as an administrator
|
||||
2. Navigate to **Home > Setup > Modules/Applications**
|
||||
3. Find **MokoDoliDymo** under the **Moko Consulting** family
|
||||
4. Click **Activate**
|
||||
|
||||
### 4. Configure Permissions
|
||||
|
||||
After activation, assign permissions to users:
|
||||
|
||||
1. Go to **Home > Users & Groups**
|
||||
2. Select the user or group
|
||||
3. Under **Permissions**, find **MokoDoliDymo** and enable:
|
||||
- **Read label templates** — view existing labels
|
||||
- **Create/Update label templates** — design and edit labels
|
||||
- **Delete label templates** — remove labels
|
||||
- **Print labels** — send labels to the printer
|
||||
|
||||
### 5. Configure Module Settings
|
||||
|
||||
1. Go to **Home > Setup > Modules/Applications**
|
||||
2. Click on **MokoDoliDymo** to access settings
|
||||
3. Configure printer connection and default label sizes
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Verify the module directory is named `mokodolidymo` (lowercase)
|
||||
- Clear Dolibarr cache and refresh
|
||||
- Check PHP syntax: `php -l src/core/modules/modMokoDoliDymo.class.php`
|
||||
- Ensure `$dolibarr_main_document_root_alt` is set in `conf/conf.php`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure the web server user has read access to all module files
|
||||
- Verify the module is activated before assigning permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
1. Go to **Home > Setup > Modules/Applications**
|
||||
2. Find **MokoDoliDymo** and click **Deactivate**
|
||||
3. Optionally remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/mokodolidymo
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Read the [Development Guide](development.md) if you want to extend the module
|
||||
- Check the [Changelog](changelog.md) for version history
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,34 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
## MokoDoliDymo Module ID
|
||||
|
||||
**Module ID: 185072** — registered in the [Moko Consulting module registry](https://github.com/mokoconsulting-tech/moko-platform/blob/main/docs/development/crm/module-registry.md).
|
||||
|
||||
This ID is **permanent and immutable**. It is stored in `$this->numero` in the module descriptor and must never be changed after deployment. Changing it would break all existing Dolibarr installations using this module.
|
||||
|
||||
## Dolibarr Module ID Ranges
|
||||
|
||||
| Range | Purpose |
|
||||
|-------|---------|
|
||||
| 0 – 94,999 | Core Dolibarr modules |
|
||||
| 95,000 – 99,999 | Community modules (official repos) |
|
||||
| 100,000 – 499,999 | Third-party public modules |
|
||||
| 500,000 – 599,999 | Private/unlisted modules |
|
||||
| 600,000+ | Development/temporary (never distribute) |
|
||||
|
||||
MokoDoliDymo's ID (185072) falls in the third-party public range.
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Moko Consulting Module Registry](https://github.com/mokoconsulting-tech/moko-platform/blob/main/docs/development/crm/module-registry.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliDymo](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliDymo) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,47 @@
|
||||
← [Home](Home)
|
||||
|
||||
# CHANGELOG FOR MODULE MOKODOLIG
|
||||
|
||||
## [01.00.00] - Unreleased
|
||||
### Added
|
||||
- Initial module structure following [moko-platform](https://github.com/mokoconsulting-tech/MokoCodingDefaults)
|
||||
- Core module descriptor with Google services focus
|
||||
- **License key validation system** - Requires valid license from Moko release system
|
||||
- License management interface in admin setup page
|
||||
- Admin pages (setup, tools, about) for configuration
|
||||
- Language files (en_US) with Google services terminology
|
||||
- Development scripts (build, test, run)
|
||||
- Validation scripts for code quality
|
||||
- PHPUnit test infrastructure
|
||||
- Security hardening with blank index files
|
||||
- OAuth 2.0 authentication framework placeholder
|
||||
- Google Sign-In / SSO authentication integration
|
||||
- User auto-provisioning from Google accounts
|
||||
- Gmail API integration foundation
|
||||
- Google Drive integration foundation
|
||||
- Automated Dolibarr backup upload to Google Drive
|
||||
- Backup retention and management system
|
||||
- Google Calendar sync foundation
|
||||
- Google Meet integration foundation
|
||||
- Google Voice integration foundation
|
||||
|
||||
### Changed
|
||||
- N/A
|
||||
|
||||
### Fixed
|
||||
- N/A
|
||||
|
||||
### Security
|
||||
- OAuth 2.0 authentication preparation
|
||||
- Token encryption infrastructure
|
||||
- Secure API communication setup
|
||||
|
||||
## 01.00.00
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliG](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliG) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,247 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliG Development Guide
|
||||
|
||||
## Overview
|
||||
|
||||
MokoDoliG is a comprehensive Google Workspace integration module for Dolibarr, providing:
|
||||
- Google Sign-In / OAuth authentication
|
||||
- Gmail integration
|
||||
- Google Drive file management and automated backup uploads
|
||||
- Google Calendar synchronization
|
||||
- Google Meet video conferencing
|
||||
- Google Voice telephony
|
||||
|
||||
This project follows [moko-platform (MokoCodingDefaults)](https://github.com/mokoconsulting-tech/MokoCodingDefaults) for coding conventions, project structure, and best practices.
|
||||
|
||||
## Module Information
|
||||
|
||||
- **Module ID**: 185057
|
||||
- **Version**: 01.00.00
|
||||
- **License**: GPL-3.0-or-later
|
||||
- **Vendor**: Moko Consulting
|
||||
|
||||
## Repository Structure
|
||||
|
||||
The repository follows both Dolibarr standards and modern PHP practices:
|
||||
|
||||
### Dolibarr Standard Directories
|
||||
|
||||
- `admin/` - Administrative interface pages (setup, tools, about)
|
||||
- `core/modules/` - Module descriptor (modMokoDoliG.class.php)
|
||||
- `class/` - Dolibarr-style classes (for compatibility)
|
||||
- `lib/` - Library functions and helpers
|
||||
- `langs/` - Language files (en_US)
|
||||
- `css/` - Stylesheets
|
||||
- `js/` - JavaScript files
|
||||
- `img/` - Images and logos
|
||||
- `sql/` - Database schemas and update scripts
|
||||
- `migrations/` - Data migration scripts
|
||||
|
||||
### Modern PHP Structure
|
||||
|
||||
- `src/` - PSR-4 autoloaded modern PHP classes
|
||||
- `Auth/` - Google authentication (GoogleAuthenticator)
|
||||
- `Services/` - Google service integrations (Gmail, Drive, Calendar, Meet, Voice)
|
||||
- `Backup/` - Backup management (BackupManager)
|
||||
- `Helpers/` - Utility classes
|
||||
|
||||
### Development Infrastructure
|
||||
|
||||
- `tests/` - PHPUnit tests
|
||||
- `scripts/dev/` - Development scripts (build, test, run)
|
||||
- `scripts/validate/` - Validation scripts (syntax, changelog, versions, security)
|
||||
- Configuration: composer.json, phpcs.xml, phpstan.neon, phpunit.xml
|
||||
- Standards: .editorconfig, .gitignore, .gitattributes
|
||||
|
||||
## Features Implemented
|
||||
|
||||
### ✅ Repository Structure
|
||||
- Complete Dolibarr-compliant directory structure
|
||||
- Modern `src/` directory with PSR-4 namespacing
|
||||
- Security hardening with blank index files in all directories
|
||||
- Proper .htaccess configuration
|
||||
|
||||
### ✅ Module Descriptor
|
||||
- Module ID: 185057
|
||||
- Complete metadata and configuration
|
||||
- Permission structure
|
||||
- Menu integration ready
|
||||
|
||||
### ✅ Admin Interface
|
||||
- Setup page for configuration
|
||||
- Tools page for utilities
|
||||
- About page for information
|
||||
- Tabbed navigation system
|
||||
|
||||
### ✅ Google Services Foundation
|
||||
|
||||
#### Authentication (src/Auth/)
|
||||
- GoogleAuthenticator class for OAuth 2.0
|
||||
- Single Sign-On (SSO) support
|
||||
- User auto-provisioning
|
||||
- Domain restrictions
|
||||
- Account linking/unlinking
|
||||
|
||||
#### Google Drive (src/Services/Drive/)
|
||||
- DriveService class for file operations
|
||||
- Upload/download capabilities
|
||||
- Folder management
|
||||
- File sharing
|
||||
|
||||
#### Backup Management (src/Backup/)
|
||||
- BackupManager class
|
||||
- Automated backup uploads to Google Drive
|
||||
- Retention policies
|
||||
- Backup listing and management
|
||||
|
||||
### ✅ Development Tools
|
||||
- Build script (syntax check, PHPCS, PHPStan)
|
||||
- Test runner (PHPUnit)
|
||||
- Development server launcher
|
||||
- Validation scripts for code quality
|
||||
|
||||
### ✅ Documentation
|
||||
- Comprehensive README with features and usage
|
||||
- CHANGELOG with version history
|
||||
- CONTRIBUTING guidelines
|
||||
- CODE_OF_CONDUCT
|
||||
- This DEVELOPMENT guide
|
||||
|
||||
### ✅ Testing Infrastructure
|
||||
- PHPUnit configuration
|
||||
- Test bootstrap
|
||||
- Example test class
|
||||
- Test scripts
|
||||
|
||||
### ✅ Code Quality Tools
|
||||
- PHP CodeSniffer (PSR-12)
|
||||
- PHPStan (Level 5)
|
||||
- EditorConfig
|
||||
- Validation scripts
|
||||
|
||||
## Next Steps (TODO)
|
||||
|
||||
### Google API Integration
|
||||
- [ ] Implement actual Google API client library integration
|
||||
- [ ] Complete OAuth token exchange
|
||||
- [ ] User info retrieval from Google
|
||||
- [ ] Gmail API implementation
|
||||
- [ ] Calendar API implementation
|
||||
- [ ] Meet API implementation
|
||||
- [ ] Voice API implementation
|
||||
|
||||
### Authentication
|
||||
- [ ] Database schema for Google account linking
|
||||
- [ ] Login page integration
|
||||
- [ ] User provisioning logic
|
||||
- [ ] Session management
|
||||
- [ ] OAuth callback handler
|
||||
|
||||
### Backup System
|
||||
- [ ] Database table for backup tracking
|
||||
- [ ] Scheduled uploads (cron)
|
||||
- [ ] Retention policy implementation
|
||||
- [ ] Backup restoration
|
||||
- [ ] Encryption support
|
||||
|
||||
### Testing
|
||||
- [ ] Unit tests for all classes
|
||||
- [ ] Integration tests with Google APIs
|
||||
- [ ] Mock Google API responses
|
||||
- [ ] End-to-end testing
|
||||
|
||||
### UI/UX
|
||||
- [ ] Configuration wizard
|
||||
- [ ] Connection status indicators
|
||||
- [ ] Sync progress indicators
|
||||
- [ ] Error handling and user feedback
|
||||
- [ ] Module logo/icon
|
||||
|
||||
## Development Workflow
|
||||
|
||||
1. **Install dependencies**:
|
||||
```bash
|
||||
composer install
|
||||
```
|
||||
|
||||
2. **Run build checks**:
|
||||
```bash
|
||||
./scripts/dev/build.sh
|
||||
```
|
||||
|
||||
3. **Run tests**:
|
||||
```bash
|
||||
./scripts/dev/test.sh
|
||||
```
|
||||
|
||||
4. **Validate code**:
|
||||
```bash
|
||||
./scripts/validate/php_syntax.sh
|
||||
./scripts/validate/version_alignment.sh
|
||||
./scripts/validate/changelog.sh
|
||||
./scripts/validate/paths.sh
|
||||
```
|
||||
|
||||
5. **Development server** (for testing outside Dolibarr):
|
||||
```bash
|
||||
./scripts/dev/run.sh
|
||||
```
|
||||
|
||||
## Integration with Dolibarr
|
||||
|
||||
To install and test with Dolibarr:
|
||||
|
||||
1. Copy the module to Dolibarr's custom directory:
|
||||
```bash
|
||||
cp -r . /path/to/dolibarr/htdocs/custom/mokodolig/
|
||||
```
|
||||
|
||||
2. Log in to Dolibarr as administrator
|
||||
|
||||
3. Go to: Home → Setup → Modules/Applications
|
||||
|
||||
4. Find "MokoDoliG" and activate it
|
||||
|
||||
5. Configure Google credentials in module settings
|
||||
|
||||
## Google API Setup
|
||||
|
||||
1. Create project in Google Cloud Console
|
||||
2. Enable required APIs:
|
||||
- Gmail API
|
||||
- Google Drive API
|
||||
- Google Calendar API
|
||||
- People API (for user info)
|
||||
3. Create OAuth 2.0 credentials
|
||||
4. Add authorized redirect URI: `https://your-dolibarr.com/custom/mokodolig/oauth/callback.php`
|
||||
5. Configure OAuth consent screen
|
||||
|
||||
## Security Considerations
|
||||
|
||||
- OAuth tokens stored encrypted
|
||||
- Domain restrictions for SSO
|
||||
- Input validation on all forms
|
||||
- CSRF protection
|
||||
- Rate limiting for API calls
|
||||
- Audit logging
|
||||
|
||||
## Contributing
|
||||
|
||||
See [CONTRIBUTING.md](CONTRIBUTING.md) for contribution guidelines.
|
||||
|
||||
## Support
|
||||
|
||||
For questions or issues, contact: hello@mokoconsulting.tech
|
||||
|
||||
---
|
||||
|
||||
© 2025 Moko Consulting | GPL-3.0-or-later
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliG](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliG) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,30 @@
|
||||
# MokoDoliG
|
||||
|
||||
A Dolibarr module to extend the interface to Google Workspace.
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliG) |
|
||||
|
||||
---
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [CHANGELOG](CHANGELOG) | ← [Home](Home) |
|
||||
| [DEVELOPMENT](DEVELOPMENT) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliG](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliG) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliG/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliG](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliG) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,43 @@
|
||||
# MokoDoliGithub
|
||||
|
||||
A Dolibarr module to bridge to Github
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [installation](installation) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [changelog](changelog) | ← [Home](Home) |
|
||||
| [development](development) | ← [Home](Home) |
|
||||
| [module id policy](module-id-policy.-.-) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,148 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Documentation Index
|
||||
|
||||
Welcome to the moko-platform Dolibarr Template documentation. This guide will help you navigate all available documentation resources.
|
||||
|
||||
## Quick Links
|
||||
|
||||
- [Installation Guide](installation.md) - Get started with installing the template
|
||||
- [Development Guide](development.md) - Learn how to develop Dolibarr modules
|
||||
- [Module ID Policy](module-id-policy.md) - Understand module ID assignment process
|
||||
- [Changelog](changelog.md) - Track version history and changes
|
||||
|
||||
## Documentation Structure
|
||||
|
||||
### For New Users
|
||||
|
||||
If you're new to this template, start here:
|
||||
|
||||
1. **[Installation Guide](installation.md)**
|
||||
- Prerequisites and requirements
|
||||
- Step-by-step installation instructions
|
||||
- Configuration and setup
|
||||
- Troubleshooting common issues
|
||||
|
||||
2. **[Module ID Policy](module-id-policy.md)**
|
||||
- Understanding module IDs
|
||||
- Development vs. production IDs
|
||||
- How to request an official ID
|
||||
- Best practices
|
||||
|
||||
### For Developers
|
||||
|
||||
If you're developing a module, these guides will help:
|
||||
|
||||
1. **[Development Guide](development.md)**
|
||||
- Module structure and organization
|
||||
- Module descriptor configuration
|
||||
- Coding standards and best practices
|
||||
- Security guidelines
|
||||
- Database operations
|
||||
- Testing and debugging
|
||||
|
||||
2. **[Contributing Guidelines](CONTRIBUTING)**
|
||||
- How to contribute
|
||||
- Code standards
|
||||
- Pull request process
|
||||
- Commit message guidelines
|
||||
|
||||
### Reference Materials
|
||||
|
||||
- **[Changelog](changelog.md)** - Version history and release notes
|
||||
- **[README](README)** - Project overview and quick start
|
||||
|
||||
## Getting Help
|
||||
|
||||
### Common Questions
|
||||
|
||||
**Q: Where do I start?**
|
||||
A: Begin with the [Installation Guide](installation.md) to set up the template, then review the [Development Guide](development.md) for building your module.
|
||||
|
||||
**Q: What module ID should I use?**
|
||||
A: Use an ID greater than 600,000 during development. See the [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
**Q: How do I contribute?**
|
||||
A: Check out the [Contributing Guidelines](CONTRIBUTING) for the complete process.
|
||||
|
||||
**Q: Where are the code examples?**
|
||||
A: The [Development Guide](development.md) contains numerous code examples and best practices.
|
||||
|
||||
### Support Resources
|
||||
|
||||
- **GitHub Issues**: Report bugs or request features
|
||||
- **Dolibarr Forum**: https://www.dolibarr.org/forum
|
||||
- **Dolibarr Wiki**: https://wiki.dolibarr.org/
|
||||
- **Dolibarr Documentation**: https://www.dolibarr.org/doc/html/
|
||||
|
||||
## External Resources
|
||||
|
||||
### Official Dolibarr Documentation
|
||||
|
||||
- [Developer Documentation](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [API Reference](https://www.dolibarr.org/doc/html/)
|
||||
|
||||
### moko-platform
|
||||
|
||||
- [MokoConsulting Tech GitHub](https://github.com/mokoconsulting-tech)
|
||||
- Template Repository: [moko-platform-Template-Dolibarr](https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr)
|
||||
|
||||
## Documentation Conventions
|
||||
|
||||
Throughout this documentation, you'll see these conventions:
|
||||
|
||||
- **Bold text**: Important concepts or required fields
|
||||
- `Code formatting`: File names, code snippets, commands
|
||||
- > Blockquotes: Important notes or warnings
|
||||
- ✅ Checkmarks: Best practices or recommended actions
|
||||
- ❌ Cross marks: Things to avoid
|
||||
|
||||
### Code Examples
|
||||
|
||||
Code examples use syntax highlighting and include comments:
|
||||
|
||||
```php
|
||||
// Example PHP code with explanation
|
||||
$this->numero = 600001; // Development module ID
|
||||
```
|
||||
|
||||
```bash
|
||||
# Example command line operations
|
||||
cd /path/to/dolibarr/
|
||||
git clone repo-url
|
||||
```
|
||||
|
||||
## Contributing to Documentation
|
||||
|
||||
Found an error or want to improve the documentation?
|
||||
|
||||
1. Fork the repository
|
||||
2. Edit the relevant markdown file
|
||||
3. Submit a pull request
|
||||
4. Follow the [Contributing Guidelines](CONTRIBUTING)
|
||||
|
||||
Good documentation helps everyone!
|
||||
|
||||
## Version Information
|
||||
|
||||
- **Template Version**: 1.0.0
|
||||
- **Last Updated**: 2026-01-16
|
||||
- **Minimum Dolibarr Version**: 12.0
|
||||
- **PHP Version**: 7.4+
|
||||
|
||||
---
|
||||
|
||||
**Next Steps**:
|
||||
- New to the template? Start with [Installation Guide](installation.md)
|
||||
- Ready to develop? Check out [Development Guide](development.md)
|
||||
- Need to request a module ID? Review [Module ID Policy](module-id-policy.md)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,70 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Changelog
|
||||
|
||||
All notable changes to this project template will be documented in this file.
|
||||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
### Added
|
||||
- Comprehensive README.md with project overview and usage instructions
|
||||
- Module ID policy documentation
|
||||
- Installation guide with detailed setup instructions
|
||||
- Development guide with best practices and examples
|
||||
- Contributing guidelines
|
||||
- Documentation structure following moko-platform
|
||||
|
||||
## [1.0.0] - 2026-01-16
|
||||
|
||||
### Added
|
||||
- Initial template structure for Dolibarr modules
|
||||
- Basic documentation framework
|
||||
- Module ID policy requiring issue-based requests
|
||||
- Support for temporary development IDs (600,000+)
|
||||
|
||||
---
|
||||
|
||||
## Template Usage Notes
|
||||
|
||||
When using this template for your module:
|
||||
|
||||
1. Copy this changelog to your project
|
||||
2. Update the version numbers as you develop
|
||||
3. Document all changes in the appropriate category:
|
||||
- **Added** for new features
|
||||
- **Changed** for changes in existing functionality
|
||||
- **Deprecated** for soon-to-be removed features
|
||||
- **Removed** for now removed features
|
||||
- **Fixed** for any bug fixes
|
||||
- **Security** for vulnerability fixes
|
||||
|
||||
Example entry:
|
||||
```markdown
|
||||
## [1.1.0] - 2026-02-15
|
||||
|
||||
### Added
|
||||
- New feature X for handling Y
|
||||
- Support for Z functionality
|
||||
|
||||
### Fixed
|
||||
- Bug in module activation
|
||||
- Permission check in admin page
|
||||
|
||||
### Changed
|
||||
- Updated module descriptor format
|
||||
- Improved error handling
|
||||
```
|
||||
|
||||
[Unreleased]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/compare/v1.0.0...HEAD
|
||||
[1.0.0]: https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr/releases/tag/v1.0.0
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,323 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Development Guide
|
||||
|
||||
This guide provides best practices and guidelines for developing Dolibarr modules using this template.
|
||||
|
||||
## Module Structure
|
||||
|
||||
A well-organized Dolibarr module follows this structure:
|
||||
|
||||
```
|
||||
yourmodule/
|
||||
├── class/ # Business logic classes
|
||||
│ ├── yourmodule.class.php # Main business object
|
||||
│ └── api_yourmodule.class.php # REST API endpoints (optional)
|
||||
├── core/ # Core integrations
|
||||
│ ├── modules/ # Numbering modules
|
||||
│ └── triggers/ # Event triggers
|
||||
│ └── interface_99_modYourmodule_YourmoduleTriggers.class.php
|
||||
├── lang/ # Translations
|
||||
│ ├── en_US/
|
||||
│ │ └── yourmodule.lang
|
||||
│ └── fr_FR/
|
||||
│ └── yourmodule.lang
|
||||
├── sql/ # Database scripts
|
||||
│ ├── llx_yourmodule_table.sql
|
||||
│ └── llx_yourmodule_table.key.sql
|
||||
├── css/ # Stylesheets
|
||||
│ └── yourmodule.css
|
||||
├── js/ # JavaScript
|
||||
│ └── yourmodule.js
|
||||
├── img/ # Images and icons
|
||||
│ └── object_yourmodule.png
|
||||
├── lib/ # Helper functions
|
||||
│ └── yourmodule.lib.php
|
||||
├── docs/ # Documentation
|
||||
├── admin/ # Admin pages
|
||||
│ ├── setup.php # Configuration page
|
||||
│ └── about.php # About page
|
||||
├── yourmodule_page.php # Main module page
|
||||
├── modYourmodule.class.php # Module descriptor
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Module Descriptor
|
||||
|
||||
The module descriptor (`modYourmodule.class.php`) is the core configuration file.
|
||||
|
||||
### Essential Properties
|
||||
|
||||
```php
|
||||
<?php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
global $langs, $conf;
|
||||
$this->db = $db;
|
||||
|
||||
// Module ID - use 600,000+ for development
|
||||
$this->numero = 600001;
|
||||
|
||||
// Module identification
|
||||
$this->rights_class = 'yourmodule';
|
||||
$this->family = "other";
|
||||
$this->module_position = '1000';
|
||||
|
||||
// Module name and description
|
||||
$this->name = preg_replace('/^mod/i', '', get_class($this));
|
||||
$this->description = "Module description";
|
||||
$this->descriptionlong = "Detailed module description";
|
||||
|
||||
// Version
|
||||
$this->version = '1.0.0';
|
||||
$this->const_name = 'MAIN_MODULE_' . strtoupper($this->name);
|
||||
|
||||
// Dependencies
|
||||
$this->depends = array(); // e.g., array('modThirdparty', 'modProduct')
|
||||
$this->requiredby = array();
|
||||
$this->conflictwith = array();
|
||||
|
||||
// Language files
|
||||
$this->langfiles = array("yourmodule@yourmodule");
|
||||
|
||||
// Configuration page
|
||||
$this->config_page_url = array("setup.php@yourmodule");
|
||||
|
||||
// Constants
|
||||
$this->const = array();
|
||||
|
||||
// Permissions
|
||||
$this->rights = array();
|
||||
$r = 0;
|
||||
|
||||
$this->rights[$r][0] = $this->numero . sprintf("%02d", $r + 1);
|
||||
$this->rights[$r][1] = 'Read objects of YourModule';
|
||||
$this->rights[$r][4] = 'yourmodule';
|
||||
$this->rights[$r][5] = 'read';
|
||||
$r++;
|
||||
|
||||
// Menus
|
||||
$this->menu = array();
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Best Practices
|
||||
|
||||
### 1. Coding Standards
|
||||
|
||||
Follow Dolibarr coding standards:
|
||||
|
||||
- **Indentation**: Use tabs for indentation
|
||||
- **Naming**: Use camelCase for functions, lowercase for files
|
||||
- **Comments**: Use PHPDoc format for documentation
|
||||
- **Security**: Always sanitize inputs and escape outputs
|
||||
|
||||
Example:
|
||||
|
||||
```php
|
||||
/**
|
||||
* Get list of objects
|
||||
*
|
||||
* @param string $sortfield Sort field
|
||||
* @param string $sortorder Sort order
|
||||
* @param int $limit Limit
|
||||
* @param int $offset Offset
|
||||
* @return array Array of objects
|
||||
*/
|
||||
public function fetchAll($sortfield = 's.rowid', $sortorder = 'ASC', $limit = 0, $offset = 0)
|
||||
{
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
// Add security and parameters
|
||||
}
|
||||
```
|
||||
|
||||
### 2. Security
|
||||
|
||||
Always implement proper security:
|
||||
|
||||
```php
|
||||
// Check permissions
|
||||
if (!$user->rights->yourmodule->read) {
|
||||
accessforbidden();
|
||||
}
|
||||
|
||||
// Sanitize inputs
|
||||
$id = GETPOST('id', 'int');
|
||||
$name = GETPOST('name', 'alpha');
|
||||
|
||||
// Use prepared statements
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "table WHERE id = " . (int)$id;
|
||||
|
||||
// Escape output
|
||||
print dol_escape_htmltag($user_input);
|
||||
```
|
||||
|
||||
**Important**: Review our [Security Policy](SECURITY) for comprehensive security guidelines and best practices.
|
||||
|
||||
### 3. Database Operations
|
||||
|
||||
Use Dolibarr's database abstraction:
|
||||
|
||||
```php
|
||||
// Insert
|
||||
$sql = "INSERT INTO " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " (field1, field2) VALUES ('" . $this->db->escape($value1) . "', '" . $this->db->escape($value2) . "')";
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Update
|
||||
$sql = "UPDATE " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$sql .= " SET field1 = '" . $this->db->escape($value) . "'";
|
||||
$sql .= " WHERE rowid = " . (int)$id;
|
||||
$resql = $this->db->query($sql);
|
||||
|
||||
// Select
|
||||
$sql = "SELECT * FROM " . MAIN_DB_PREFIX . "yourmodule_table";
|
||||
$resql = $this->db->query($sql);
|
||||
if ($resql) {
|
||||
$num = $this->db->num_rows($resql);
|
||||
while ($i < $num) {
|
||||
$obj = $this->db->fetch_object($resql);
|
||||
// Process object
|
||||
$i++;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 4. Translations
|
||||
|
||||
Use translation keys in language files:
|
||||
|
||||
```php
|
||||
// In lang/en_US/yourmodule.lang
|
||||
YourModuleSetup = Your Module Setup
|
||||
YourModuleDescription = This is your module
|
||||
```
|
||||
|
||||
```php
|
||||
// In PHP code
|
||||
$langs->load("yourmodule@yourmodule");
|
||||
print $langs->trans("YourModuleSetup");
|
||||
```
|
||||
|
||||
### 5. Hooks and Triggers
|
||||
|
||||
Implement triggers for event handling:
|
||||
|
||||
```php
|
||||
class InterfaceModYourmoduleTriggers
|
||||
{
|
||||
public function runTrigger($action, $object, $user, $langs, $conf)
|
||||
{
|
||||
if ($action == 'BILL_CREATE') {
|
||||
// Handle invoice creation
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 6. API Development
|
||||
|
||||
Create REST API endpoints:
|
||||
|
||||
```php
|
||||
class YourModuleApi extends DolibarrApi
|
||||
{
|
||||
/**
|
||||
* @url GET /yourmodule/objects
|
||||
*/
|
||||
public function index($sortfield = "t.rowid", $sortorder = 'ASC', $limit = 100, $page = 0)
|
||||
{
|
||||
// Implement API logic
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Testing
|
||||
|
||||
### Manual Testing
|
||||
|
||||
1. Test module activation/deactivation
|
||||
2. Verify permissions work correctly
|
||||
3. Check database operations
|
||||
4. Test with different user roles
|
||||
5. Verify translations
|
||||
|
||||
### Debugging
|
||||
|
||||
Enable Dolibarr debugging:
|
||||
|
||||
```php
|
||||
// In conf/conf.php
|
||||
$dolibarr_main_prod = 0; // Development mode
|
||||
```
|
||||
|
||||
View logs in `/documents/dolibarr.log`
|
||||
|
||||
## Module ID Management
|
||||
|
||||
### Development Phase
|
||||
|
||||
Use module ID > 600,000:
|
||||
|
||||
```php
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Before Distribution
|
||||
|
||||
1. Create an issue in the repository requesting a module ID
|
||||
2. Wait for approval and assignment
|
||||
3. Update the module descriptor with the assigned ID
|
||||
4. Test thoroughly before release
|
||||
|
||||
See [Module ID Policy](module-id-policy.md) for details.
|
||||
|
||||
## Version Control
|
||||
|
||||
Follow semantic versioning (MAJOR.MINOR.PATCH):
|
||||
|
||||
- **MAJOR**: Breaking changes
|
||||
- **MINOR**: New features (backward compatible)
|
||||
- **PATCH**: Bug fixes
|
||||
|
||||
Update version in:
|
||||
- `modYourmodule.class.php`
|
||||
- `docs/changelog.md`
|
||||
- Documentation files
|
||||
|
||||
## Publishing
|
||||
|
||||
Before publishing your module:
|
||||
|
||||
1. ✅ Request and receive official module ID
|
||||
2. ✅ Complete all documentation
|
||||
3. ✅ Test on multiple Dolibarr versions
|
||||
4. ✅ Review security best practices
|
||||
5. ✅ Add license file
|
||||
6. ✅ Update changelog
|
||||
7. ✅ Create release notes
|
||||
|
||||
## Resources
|
||||
|
||||
- [Dolibarr Developer Docs](https://wiki.dolibarr.org/index.php/Developer_documentation)
|
||||
- [Module Development Guide](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr API Reference](https://www.dolibarr.org/doc/html/)
|
||||
- [Module ID Registry](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
## Support
|
||||
|
||||
- Repository issues for template questions
|
||||
- [Dolibarr Forum](https://www.dolibarr.org/forum) for development help
|
||||
- [Dolibarr GitHub](https://github.com/Dolibarr/dolibarr) for core issues
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,173 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Installation Guide
|
||||
|
||||
This guide provides detailed instructions for installing and configuring your Dolibarr module.
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing the module, ensure you have:
|
||||
|
||||
- **Dolibarr ERP/CRM**: Version 12.0 or higher
|
||||
- **PHP**: Version 7.4 or higher
|
||||
- **Web Server**: Apache 2.4+ or Nginx 1.18+
|
||||
- **Database**: MySQL 5.7+, MariaDB 10.3+, or PostgreSQL 11+
|
||||
- **PHP Extensions**:
|
||||
- mysqli or pgsql
|
||||
- gd or imagick
|
||||
- curl
|
||||
- json
|
||||
- xml
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### 1. Clone the Repository
|
||||
|
||||
Navigate to your Dolibarr's custom directory:
|
||||
|
||||
```bash
|
||||
cd /path/to/dolibarr/htdocs/custom/
|
||||
```
|
||||
|
||||
Clone this template repository:
|
||||
|
||||
```bash
|
||||
git clone https://github.com/mokoconsulting-tech/moko-platform-Template-Dolibarr.git yourmodule
|
||||
```
|
||||
|
||||
Replace `yourmodule` with your desired module name (lowercase, no spaces).
|
||||
|
||||
### 2. Rename and Configure
|
||||
|
||||
Navigate to the module directory:
|
||||
|
||||
```bash
|
||||
cd yourmodule
|
||||
```
|
||||
|
||||
Rename the module descriptor file:
|
||||
|
||||
```bash
|
||||
mv modYourmodule.class.php modYourModuleName.class.php
|
||||
```
|
||||
|
||||
### 3. Configure Module ID
|
||||
|
||||
Open the module descriptor file and set a temporary module ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourModuleName.class.php
|
||||
$this->numero = 600001; // Use a number > 600,000 for development
|
||||
```
|
||||
|
||||
**Important:** Before publishing, request an official module ID by creating an issue in the repository.
|
||||
|
||||
### 4. Set File Permissions
|
||||
|
||||
Ensure proper file permissions:
|
||||
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
|
||||
# Set directory permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find /path/to/dolibarr/htdocs/custom/yourmodule -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
### 5. Enable the Module in Dolibarr
|
||||
|
||||
1. Log in to your Dolibarr instance as an administrator
|
||||
2. Navigate to **Home → Setup → Modules/Applications**
|
||||
3. Find your module in the list
|
||||
4. Click the **Activate** button
|
||||
|
||||
### 6. Configure Module Settings (if applicable)
|
||||
|
||||
After activation:
|
||||
|
||||
1. Go to **Home → Setup → Modules/Applications**
|
||||
2. Click on your module name to access its configuration page
|
||||
3. Configure any required settings
|
||||
4. Save changes
|
||||
|
||||
## Database Setup
|
||||
|
||||
If your module requires database tables:
|
||||
|
||||
### Automatic Setup
|
||||
|
||||
The module descriptor can handle automatic table creation during activation. Ensure your SQL files are in the `sql/` directory:
|
||||
|
||||
```
|
||||
sql/
|
||||
├── llx_yourmodule_table.sql
|
||||
└── llx_yourmodule_table.key.sql
|
||||
```
|
||||
|
||||
### Manual Setup
|
||||
|
||||
Alternatively, run SQL scripts manually:
|
||||
|
||||
```bash
|
||||
mysql -u username -p database_name < sql/llx_yourmodule_table.sql
|
||||
```
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing
|
||||
|
||||
- Clear Dolibarr cache: Delete `/documents/install.lock` and refresh
|
||||
- Check file permissions
|
||||
- Verify PHP syntax errors: `php -l modYourModuleName.class.php`
|
||||
|
||||
### Permission Errors
|
||||
|
||||
- Ensure Apache/Nginx user has read access to all module files
|
||||
- Check `conf.php` file permissions in Dolibarr root
|
||||
|
||||
### Database Errors
|
||||
|
||||
- Verify database credentials in Dolibarr's `conf/conf.php`
|
||||
- Check SQL file syntax
|
||||
- Ensure database user has CREATE TABLE permissions
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To remove the module:
|
||||
|
||||
1. Navigate to **Home → Setup → Modules/Applications**
|
||||
2. Find your module and click **Deactivate**
|
||||
3. Optionally, remove the module directory:
|
||||
```bash
|
||||
rm -rf /path/to/dolibarr/htdocs/custom/yourmodule
|
||||
```
|
||||
|
||||
**Note:** Deactivating the module does not remove database tables. To remove data:
|
||||
|
||||
```sql
|
||||
DROP TABLE llx_yourmodule_table;
|
||||
```
|
||||
|
||||
## Next Steps
|
||||
|
||||
- Review the [Development Guide](development.md) to start customizing your module
|
||||
- Check the [Module ID Policy](module-id-policy.md) before distribution
|
||||
- Read the [Changelog](changelog.md) for version history
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues:
|
||||
- Create an issue in the repository
|
||||
- Check Dolibarr logs: `/documents/dolibarr.log`
|
||||
- Visit the [Dolibarr Forum](https://www.dolibarr.org/forum)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,260 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Module ID Policy
|
||||
|
||||
This document explains the module ID assignment policy for Dolibarr modules developed using this template.
|
||||
|
||||
## Overview
|
||||
|
||||
Every Dolibarr module requires a unique numeric identifier (module ID). This ID is critical for:
|
||||
- Module identification within Dolibarr
|
||||
- Preventing conflicts with other modules
|
||||
- Tracking module permissions and configurations
|
||||
- Database table prefixes and naming conventions
|
||||
|
||||
## Module ID Ranges
|
||||
|
||||
Dolibarr uses the following ID ranges:
|
||||
|
||||
| Range | Purpose | Registration Required |
|
||||
|-------|---------|----------------------|
|
||||
| 0 - 94,999 | Core Dolibarr modules | Reserved by Dolibarr core team |
|
||||
| 95,000 - 99,999 | Community modules (official repos) | Yes, via Dolibarr GitHub |
|
||||
| 100,000 - 499,999 | Third-party public modules | Yes, via official registry |
|
||||
| 500,000 - 599,999 | Private/unlisted modules | Recommended for permanent private use |
|
||||
| 600,000+ | Development/temporary modules | **Use this range during development** |
|
||||
|
||||
## Development Phase
|
||||
|
||||
### Use Temporary ID (600,000+)
|
||||
|
||||
While developing your module, always use an ID greater than 600,000:
|
||||
|
||||
```php
|
||||
// In modYourmodule.class.php
|
||||
class modYourmodule extends DolibarrModules
|
||||
{
|
||||
public function __construct($db)
|
||||
{
|
||||
$this->db = $db;
|
||||
|
||||
// Temporary development ID
|
||||
$this->numero = 600001; // or 600002, 600003, etc.
|
||||
|
||||
// ... rest of configuration
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Why Use 600,000+?
|
||||
|
||||
- **No registration required**: Immediate development without waiting for approval
|
||||
- **No conflicts**: This range is intentionally unreserved for development
|
||||
- **Easy to change**: Simple to update before distribution
|
||||
- **Clear indicator**: Shows the module is in development phase
|
||||
|
||||
### Choosing Your Temporary ID
|
||||
|
||||
1. Pick any number greater than 600,000
|
||||
2. Use sequential numbers if developing multiple modules (600,001, 600,002, etc.)
|
||||
3. Document your temporary ID in your development notes
|
||||
4. Remember to replace it before distribution
|
||||
|
||||
## Production Phase
|
||||
|
||||
### Request Official Module ID
|
||||
|
||||
Before distributing or publishing your module, you **must** request an official module ID.
|
||||
|
||||
### How to Request
|
||||
|
||||
1. **Create an Issue** in this repository
|
||||
- Use the title: "Request Module ID Assignment: [Your Module Name]"
|
||||
- Use the "Module ID Request" label if available
|
||||
|
||||
2. **Provide Required Information**:
|
||||
```markdown
|
||||
## Module ID Request
|
||||
|
||||
**Module Name**: Your Module Name
|
||||
|
||||
**Description**: Brief description of what your module does
|
||||
|
||||
**Organization/Developer**: Your organization or name
|
||||
|
||||
**Distribution Plan**:
|
||||
- [ ] Public (Dolibarr Marketplace)
|
||||
- [ ] Public (GitHub/other platform)
|
||||
- [ ] Private (internal use only)
|
||||
- [ ] Commercial
|
||||
|
||||
**Target Audience**: Who will use this module?
|
||||
|
||||
**Additional Notes**: Any other relevant information
|
||||
```
|
||||
|
||||
3. **Wait for Approval**
|
||||
- A maintainer will review your request
|
||||
- You'll receive an assigned module ID
|
||||
- The ID will be from the appropriate range based on your distribution plan
|
||||
|
||||
### ID Assignment Criteria
|
||||
|
||||
Module IDs are assigned based on:
|
||||
|
||||
- **100,000 - 499,999**: Public modules intended for broad distribution
|
||||
- Dolibarr Marketplace modules
|
||||
- Open-source modules on GitHub
|
||||
- Modules with public documentation
|
||||
|
||||
- **500,000 - 599,999**: Private or limited distribution
|
||||
- Internal company modules
|
||||
- Client-specific customizations
|
||||
- Modules not intended for public use
|
||||
|
||||
### After Receiving Your ID
|
||||
|
||||
1. **Update Module Descriptor**:
|
||||
```php
|
||||
// Change from development ID
|
||||
$this->numero = 600001;
|
||||
|
||||
// To your assigned ID
|
||||
$this->numero = 123456; // Your assigned ID
|
||||
```
|
||||
|
||||
2. **Update Documentation**:
|
||||
- Update README.md with the official ID
|
||||
- Note the ID in your changelog
|
||||
- Document the assignment date
|
||||
|
||||
3. **Test Thoroughly**:
|
||||
- Reinstall module with new ID
|
||||
- Verify no conflicts with existing installations
|
||||
- Check all database operations
|
||||
|
||||
4. **Commit Changes**:
|
||||
```bash
|
||||
git add modYourmodule.class.php
|
||||
git commit -m "Update to official module ID: 123456"
|
||||
```
|
||||
|
||||
## Module ID Registry
|
||||
|
||||
### Official Dolibarr Registry
|
||||
|
||||
For modules intended for the official Dolibarr ecosystem, you may also need to register on the official wiki:
|
||||
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
|
||||
### moko-platform Registry
|
||||
|
||||
This repository maintains its own registry of assigned IDs to prevent conflicts among moko-platform projects.
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Multiple Modules
|
||||
|
||||
If you're developing multiple related modules:
|
||||
- Request a block of IDs (e.g., 123450-123459)
|
||||
- Document which ID is used by which module
|
||||
- Keep sequential IDs for related functionality
|
||||
|
||||
### Module Forking
|
||||
|
||||
If forking an existing module:
|
||||
- You **must** request a new module ID
|
||||
- Do not reuse the original module's ID
|
||||
- Document the relationship to the original module
|
||||
|
||||
### Module Renaming
|
||||
|
||||
If renaming a module:
|
||||
- Keep the same module ID
|
||||
- Update the module name and descriptor
|
||||
- Document the name change in changelog
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### ID Conflicts
|
||||
|
||||
If you experience ID conflicts:
|
||||
1. Check installed modules: `SELECT * FROM llx_const WHERE name LIKE 'MAIN_MODULE_%';`
|
||||
2. Verify your ID doesn't conflict
|
||||
3. If conflict exists, request a new ID
|
||||
4. Update and redeploy
|
||||
|
||||
### Lost or Forgotten ID
|
||||
|
||||
If you've lost track of your assigned ID:
|
||||
1. Check the issues in this repository
|
||||
2. Search module registry documentation
|
||||
3. Create a new issue asking for clarification
|
||||
|
||||
## Best Practices
|
||||
|
||||
1. ✅ **Always start with 600,000+** during development
|
||||
2. ✅ **Request official ID early** if planning to distribute
|
||||
3. ✅ **Document your ID** in all relevant files
|
||||
4. ✅ **Test after ID changes** to ensure no issues
|
||||
5. ✅ **Never use another module's ID** even in development
|
||||
6. ❌ **Don't distribute modules** with temporary IDs (600,000+)
|
||||
7. ❌ **Don't request multiple IDs** without justification
|
||||
8. ❌ **Don't change IDs** after public distribution
|
||||
|
||||
## Examples
|
||||
|
||||
### Development Stage
|
||||
```php
|
||||
// Good - using temporary development ID
|
||||
$this->numero = 600001;
|
||||
```
|
||||
|
||||
### Production Stage (Private Module)
|
||||
```php
|
||||
// Good - assigned ID from private range
|
||||
$this->numero = 550001;
|
||||
```
|
||||
|
||||
### Production Stage (Public Module)
|
||||
```php
|
||||
// Good - assigned ID from public range
|
||||
$this->numero = 125000;
|
||||
```
|
||||
|
||||
### Bad Practice
|
||||
```php
|
||||
// BAD - using another module's ID
|
||||
$this->numero = 1; // This is a core module ID!
|
||||
|
||||
// BAD - random low number
|
||||
$this->numero = 42;
|
||||
|
||||
// BAD - distributing with development ID
|
||||
$this->numero = 600001; // Only for development!
|
||||
```
|
||||
|
||||
## References
|
||||
|
||||
- [Dolibarr Module Development](https://wiki.dolibarr.org/index.php/Module_development)
|
||||
- [Dolibarr Module ID List](https://wiki.dolibarr.org/index.php/List_of_modules_id)
|
||||
- [Dolibarr Module Structure](https://wiki.dolibarr.org/index.php/Module_development#Module_descriptor)
|
||||
|
||||
## Contact
|
||||
|
||||
For questions about module ID assignment:
|
||||
- Create an issue in this repository
|
||||
- Tag it with "module-id-question"
|
||||
- Provide as much context as possible
|
||||
|
||||
---
|
||||
|
||||
**Remember**: Using the correct module ID ensures your module integrates seamlessly with Dolibarr and avoids conflicts with other modules in the ecosystem.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliGithub/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliGithub](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliGithub) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,385 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliHRM API Documentation
|
||||
|
||||
## Classes Overview
|
||||
|
||||
### MokoEmployee Class
|
||||
|
||||
Located in: `src/class/employee.class.php`
|
||||
|
||||
The MokoEmployee class manages employee records in the system.
|
||||
|
||||
#### Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
|----------|------|-------------|
|
||||
| id | int | Employee ID (primary key) |
|
||||
| ref | string | Employee reference (e.g., EMP00001) |
|
||||
| firstname | string | First name |
|
||||
| lastname | string | Last name |
|
||||
| email | string | Email address |
|
||||
| phone | string | Phone number |
|
||||
| address | string | Street address |
|
||||
| city | string | City |
|
||||
| zip | string | Zip/postal code |
|
||||
| country_code | string | Country code (ISO 3166-1 alpha-2) |
|
||||
| date_birth | timestamp | Date of birth |
|
||||
| position | string | Job position/title |
|
||||
| department | string | Department name |
|
||||
| date_hire | timestamp | Hire date |
|
||||
| date_termination | timestamp | Termination date |
|
||||
| status | int | Status (0=Draft, 1=Active, 9=Terminated) |
|
||||
| social_security_number | string | Social security number |
|
||||
| bank_account | string | Bank account number |
|
||||
| note_public | string | Public notes |
|
||||
| note_private | string | Private notes |
|
||||
|
||||
#### Methods
|
||||
|
||||
##### create($user, $notrigger = 0)
|
||||
Creates a new employee record in the database.
|
||||
|
||||
**Parameters:**
|
||||
- `$user` (User): User object performing the creation
|
||||
- `$notrigger` (int): 0 = launch triggers, 1 = disable triggers
|
||||
|
||||
**Returns:**
|
||||
- int: Employee ID if successful, negative value on error
|
||||
|
||||
**Example:**
|
||||
```php
|
||||
$employee = new MokoEmployee($db);
|
||||
$employee->firstname = 'John';
|
||||
$employee->lastname = 'Doe';
|
||||
$employee->email = 'john.doe@example.com';
|
||||
$employee->status = 1;
|
||||
$result = $employee->create($user);
|
||||
```
|
||||
|
||||
##### fetch($id, $ref = null)
|
||||
Loads an employee record from the database.
|
||||
|
||||
**Parameters:**
|
||||
- `$id` (int): Employee ID
|
||||
- `$ref` (string): Employee reference (optional, alternative to ID)
|
||||
|
||||
**Returns:**
|
||||
- int: 1 if found and loaded, 0 if not found, negative value on error
|
||||
|
||||
**Example:**
|
||||
```php
|
||||
$employee = new MokoEmployee($db);
|
||||
$result = $employee->fetch(123);
|
||||
// or
|
||||
$result = $employee->fetch(0, 'EMP00001');
|
||||
```
|
||||
|
||||
##### update($user, $notrigger = 0)
|
||||
Updates an existing employee record in the database.
|
||||
|
||||
**Parameters:**
|
||||
- `$user` (User): User object performing the update
|
||||
- `$notrigger` (int): 0 = launch triggers, 1 = disable triggers
|
||||
|
||||
**Returns:**
|
||||
- int: 1 if successful, negative value on error
|
||||
|
||||
**Example:**
|
||||
```php
|
||||
$employee = new MokoEmployee($db);
|
||||
$employee->fetch(123);
|
||||
$employee->position = 'Senior Developer';
|
||||
$result = $employee->update($user);
|
||||
```
|
||||
|
||||
##### delete($user, $notrigger = 0)
|
||||
Deletes an employee record from the database.
|
||||
|
||||
**Parameters:**
|
||||
- `$user` (User): User object performing the deletion
|
||||
- `$notrigger` (int): 0 = launch triggers, 1 = disable triggers
|
||||
|
||||
**Returns:**
|
||||
- int: 1 if successful, negative value on error
|
||||
|
||||
**Example:**
|
||||
```php
|
||||
$employee = new MokoEmployee($db);
|
||||
$employee->fetch(123);
|
||||
$result = $employee->delete($user);
|
||||
```
|
||||
|
||||
##### getNextNumRef()
|
||||
Generates the next available employee reference number.
|
||||
|
||||
**Returns:**
|
||||
- string: Next reference number (e.g., EMP00001)
|
||||
|
||||
##### getFullName()
|
||||
Returns the employee's full name with leading/trailing whitespace removed.
|
||||
|
||||
**Returns:**
|
||||
- string: Full name (Firstname Lastname, trimmed)
|
||||
|
||||
##### getLibStatut($mode = 0)
|
||||
Returns the status label for the employee.
|
||||
|
||||
**Parameters:**
|
||||
- `$mode` (int): Display mode (0-5)
|
||||
|
||||
**Returns:**
|
||||
- string: Status label with appropriate formatting
|
||||
|
||||
---
|
||||
|
||||
### MokoContract Class
|
||||
|
||||
Located in: `src/class/contract.class.php`
|
||||
|
||||
The MokoContract class manages employment contract records.
|
||||
|
||||
#### Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
|----------|------|-------------|
|
||||
| id | int | Contract ID (primary key) |
|
||||
| ref | string | Contract reference (e.g., CONT00001) |
|
||||
| fk_employee | int | Employee ID (foreign key) |
|
||||
| contract_type | string | Contract type (permanent, temporary, etc.) |
|
||||
| date_start | timestamp | Contract start date |
|
||||
| date_end | timestamp | Contract end date |
|
||||
| salary | float | Salary amount |
|
||||
| salary_currency | string | Currency code |
|
||||
| salary_period | string | Payment period (monthly, weekly, hourly) |
|
||||
| working_hours | int | Working hours per week |
|
||||
| annual_leave_days | int | Annual leave days |
|
||||
| status | int | Status (0=Draft, 1=Active, 9=Terminated) |
|
||||
| note_public | string | Public notes |
|
||||
| note_private | string | Private notes |
|
||||
|
||||
#### Methods
|
||||
|
||||
The MokoContract class implements the same CRUD methods as MokoEmployee:
|
||||
- `create($user, $notrigger = 0)`
|
||||
- `fetch($id, $ref = null)`
|
||||
- `update($user, $notrigger = 0)`
|
||||
- `delete($user, $notrigger = 0)`
|
||||
- `getNextNumRef()` - Returns references like CONT00001
|
||||
- `getLibStatut($mode = 0)`
|
||||
|
||||
---
|
||||
|
||||
### MokoPayroll Class
|
||||
|
||||
Located in: `src/class/payroll.class.php`
|
||||
|
||||
The MokoPayroll class manages payroll records.
|
||||
|
||||
#### Properties
|
||||
|
||||
| Property | Type | Description |
|
||||
|----------|------|-------------|
|
||||
| id | int | Payroll ID (primary key) |
|
||||
| ref | string | Payroll reference (e.g., PAY00001) |
|
||||
| fk_employee | int | Employee ID (foreign key) |
|
||||
| fk_contract | int | Contract ID (foreign key, optional) |
|
||||
| period_start | timestamp | Payroll period start date |
|
||||
| period_end | timestamp | Payroll period end date |
|
||||
| gross_salary | float | Gross salary amount |
|
||||
| net_salary | float | Net salary amount |
|
||||
| tax_amount | float | Tax amount |
|
||||
| social_security | float | Social security contributions |
|
||||
| bonuses | float | Bonus amount |
|
||||
| deductions | float | Deductions amount |
|
||||
| payment_date | timestamp | Payment date |
|
||||
| payment_method | string | Payment method |
|
||||
| status | int | Status (0=Draft, 1=Validated, 2=Paid, 9=Cancelled) |
|
||||
| note_public | string | Public notes |
|
||||
| note_private | string | Private notes |
|
||||
|
||||
#### Methods
|
||||
|
||||
The MokoPayroll class implements the same CRUD methods as MokoEmployee:
|
||||
- `create($user, $notrigger = 0)`
|
||||
- `fetch($id, $ref = null)`
|
||||
- `update($user, $notrigger = 0)`
|
||||
- `delete($user, $notrigger = 0)`
|
||||
- `getNextNumRef()` - Returns references like PAY00001
|
||||
- `getLibStatut($mode = 0)`
|
||||
|
||||
---
|
||||
|
||||
## Status Values
|
||||
|
||||
### Employee & Contract Status
|
||||
- `0` - Draft
|
||||
- `1` - Active
|
||||
- `9` - Terminated
|
||||
|
||||
### Payroll Status
|
||||
- `0` - Draft
|
||||
- `1` - Validated
|
||||
- `2` - Paid
|
||||
- `9` - Cancelled
|
||||
|
||||
---
|
||||
|
||||
## Database Schema
|
||||
|
||||
### llx_mokodolihrm_employee Table
|
||||
|
||||
Primary table for storing employee information.
|
||||
|
||||
**Indexes:**
|
||||
- Primary key on `rowid`
|
||||
- Unique key on `ref` + `entity`
|
||||
- Index on `entity`
|
||||
- Index on `status`
|
||||
|
||||
### llx_mokodolihrm_contract Table
|
||||
|
||||
Stores employment contract information with foreign key to employees.
|
||||
|
||||
**Indexes:**
|
||||
- Primary key on `rowid`
|
||||
- Unique key on `ref` + `entity`
|
||||
- Index on `entity`
|
||||
- Index on `fk_employee`
|
||||
- Index on `status`
|
||||
- Foreign key constraint to `llx_mokodolihrm_employee`
|
||||
|
||||
### llx_mokodolihrm_payroll Table
|
||||
|
||||
Stores payroll records with foreign keys to employees and contracts.
|
||||
|
||||
**Indexes:**
|
||||
- Primary key on `rowid`
|
||||
- Unique key on `ref` + `entity`
|
||||
- Index on `entity`
|
||||
- Index on `fk_employee`
|
||||
- Index on `fk_contract`
|
||||
- Index on `status`
|
||||
- Foreign key constraint to `llx_mokodolihrm_employee`
|
||||
- Foreign key constraint to `llx_mokodolihrm_contract`
|
||||
|
||||
---
|
||||
|
||||
## Usage Examples
|
||||
|
||||
### Creating an Employee with Contract and Payroll
|
||||
|
||||
```php
|
||||
// Load Dolibarr environment
|
||||
require_once DOL_DOCUMENT_ROOT.'/main.inc.php';
|
||||
require_once DOL_DOCUMENT_ROOT.'/custom/mokodolihrm/class/employee.class.php';
|
||||
require_once DOL_DOCUMENT_ROOT.'/custom/mokodolihrm/class/contract.class.php';
|
||||
require_once DOL_DOCUMENT_ROOT.'/custom/mokodolihrm/class/payroll.class.php';
|
||||
|
||||
// Create employee
|
||||
$employee = new MokoEmployee($db);
|
||||
$employee->firstname = 'John';
|
||||
$employee->lastname = 'Doe';
|
||||
$employee->email = 'john.doe@example.com';
|
||||
$employee->position = 'Software Developer';
|
||||
$employee->department = 'IT';
|
||||
$employee->date_hire = dol_now();
|
||||
$employee->status = 1;
|
||||
$employee_id = $employee->create($user);
|
||||
|
||||
if ($employee_id > 0) {
|
||||
// Create contract
|
||||
$contract = new MokoContract($db);
|
||||
$contract->fk_employee = $employee_id;
|
||||
$contract->contract_type = 'permanent';
|
||||
$contract->date_start = dol_now();
|
||||
$contract->salary = 5000;
|
||||
$contract->salary_currency = 'USD';
|
||||
$contract->salary_period = 'monthly';
|
||||
$contract->working_hours = 40;
|
||||
$contract->annual_leave_days = 20;
|
||||
$contract->status = 1;
|
||||
$contract_id = $contract->create($user);
|
||||
|
||||
if ($contract_id > 0) {
|
||||
// Create payroll
|
||||
$payroll = new MokoPayroll($db);
|
||||
$payroll->fk_employee = $employee_id;
|
||||
$payroll->fk_contract = $contract_id;
|
||||
$payroll->period_start = dol_time_plus_duree(dol_now(), -1, 'm');
|
||||
$payroll->period_end = dol_now();
|
||||
$payroll->gross_salary = 5000;
|
||||
$payroll->tax_amount = 750;
|
||||
$payroll->social_security = 500;
|
||||
$payroll->net_salary = 3750;
|
||||
$payroll->payment_date = dol_now();
|
||||
$payroll->payment_method = 'bank_transfer';
|
||||
$payroll->status = 2; // Paid
|
||||
$payroll_id = $payroll->create($user);
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### Listing All Active Employees
|
||||
|
||||
```php
|
||||
$sql = "SELECT rowid, ref, firstname, lastname, position, department";
|
||||
$sql .= " FROM ".MAIN_DB_PREFIX."mokodolihrm_employee";
|
||||
$sql .= " WHERE status = 1";
|
||||
$sql .= " ORDER BY lastname, firstname";
|
||||
|
||||
$resql = $db->query($sql);
|
||||
if ($resql) {
|
||||
while ($obj = $db->fetch_object($resql)) {
|
||||
echo $obj->ref.' - '.$obj->firstname.' '.$obj->lastname;
|
||||
echo ' ('.$obj->position.', '.$obj->department.')'."\n";
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Error Handling
|
||||
|
||||
All methods return negative values on error. Check the `$object->error` and `$object->errors` properties for details:
|
||||
|
||||
```php
|
||||
$result = $employee->create($user);
|
||||
if ($result < 0) {
|
||||
echo "Error: ".$employee->error;
|
||||
foreach ($employee->errors as $error) {
|
||||
echo "- ".$error."\n";
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Permissions
|
||||
|
||||
Check permissions before performing operations:
|
||||
|
||||
```php
|
||||
// Check read permission
|
||||
if ($user->rights->mokodolihrm->employee->read) {
|
||||
// Allow reading employee data
|
||||
}
|
||||
|
||||
// Check write permission
|
||||
if ($user->rights->mokodolihrm->employee->write) {
|
||||
// Allow creating/updating employee data
|
||||
}
|
||||
|
||||
// Check delete permission
|
||||
if ($user->rights->mokodolihrm->employee->delete) {
|
||||
// Allow deleting employee data
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,333 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliHRM Frequently Asked Questions (FAQ)
|
||||
|
||||
## General Questions
|
||||
|
||||
### Q: What is MokoDoliHRM?
|
||||
**A:** MokoDoliHRM is a comprehensive Human Resources Management module for Dolibarr ERP/CRM that provides tools for managing employees, employment contracts, and payroll processing.
|
||||
|
||||
### Q: What version of Dolibarr is required?
|
||||
**A:** MokoDoliHRM requires Dolibarr version 13.0 or higher and PHP 7.0 or higher.
|
||||
|
||||
### Q: Is MokoDoliHRM free?
|
||||
**A:** Yes, MokoDoliHRM is open source software released under the GNU General Public License v3.0.
|
||||
|
||||
### Q: Can I use MokoDoliHRM in a production environment?
|
||||
**A:** Yes, but we recommend thorough testing in a development environment first and ensuring you have proper backups in place.
|
||||
|
||||
## Installation & Setup
|
||||
|
||||
### Q: How do I install MokoDoliHRM?
|
||||
**A:** See the detailed [Installation Guide](INSTALLATION.md). In brief:
|
||||
1. Copy the module files to `htdocs/custom/mokodolihrm/`
|
||||
2. Set proper permissions
|
||||
3. Activate the module in Dolibarr
|
||||
4. Configure user permissions
|
||||
|
||||
### Q: The module doesn't appear in the modules list. What should I do?
|
||||
**A:**
|
||||
- Verify files are in the correct location: `htdocs/custom/mokodolihrm/`
|
||||
- Check file permissions (web server must be able to read the files)
|
||||
- Clear Dolibarr cache by removing `documents/install/locks/*.lock`
|
||||
- Refresh the modules page in your browser
|
||||
|
||||
### Q: Database tables aren't created automatically. What should I do?
|
||||
**A:**
|
||||
- Manually run the SQL script: `mysql -u username -p database < src/sql/llx_mokodolihrm.sql`
|
||||
- Replace `llx_` with your Dolibarr table prefix if different
|
||||
- Ensure your database user has CREATE TABLE privileges
|
||||
|
||||
### Q: Can I customize the module?
|
||||
**A:** Yes, the module is open source and can be modified. However, we recommend creating a fork or custom version to preserve your changes during updates.
|
||||
|
||||
## Employee Management
|
||||
|
||||
### Q: What information can I store about employees?
|
||||
**A:** Employee records include:
|
||||
- Personal information (name, birth date, address)
|
||||
- Contact details (email, phone)
|
||||
- Employment information (position, department, hire date)
|
||||
- Financial information (social security number, bank account)
|
||||
- Notes (public and private)
|
||||
|
||||
### Q: Can I track employee history?
|
||||
**A:** The module tracks creation and modification dates. For detailed history tracking, consider integrating with Dolibarr's audit log module or implementing custom triggers.
|
||||
|
||||
### Q: What happens if I delete an employee?
|
||||
**A:** ⚠️ Deleting an employee will cascade delete all associated contracts and payroll records. Consider setting the status to "Terminated" instead.
|
||||
|
||||
### Q: Can I import employees from another system?
|
||||
**A:** The module doesn't include built-in import functionality. Options include:
|
||||
- Manual entry for small numbers of employees
|
||||
- Using Dolibarr's import module
|
||||
- Writing a custom import script using the API
|
||||
- Direct database import (requires technical knowledge)
|
||||
|
||||
### Q: How do I handle employee promotions or role changes?
|
||||
**A:**
|
||||
1. Edit the employee record to update position and department
|
||||
2. Create a new contract reflecting the new terms
|
||||
3. Terminate or end the old contract
|
||||
|
||||
## Contract Management
|
||||
|
||||
### Q: What types of contracts are supported?
|
||||
**A:** The module supports:
|
||||
- Permanent (full-time, ongoing)
|
||||
- Temporary (fixed-term)
|
||||
- Consultant (contract-based)
|
||||
- Intern (training/educational)
|
||||
|
||||
You can also enter custom contract types.
|
||||
|
||||
### Q: Can an employee have multiple contracts?
|
||||
**A:** Yes, an employee can have multiple contracts (e.g., historical contracts, concurrent part-time positions).
|
||||
|
||||
### Q: How do I handle contract renewals?
|
||||
**A:**
|
||||
1. Set an end date on the current contract
|
||||
2. Create a new contract with the new terms and start date
|
||||
3. Both contracts remain in the system for historical tracking
|
||||
|
||||
### Q: Can I track probation periods?
|
||||
**A:** While there's no dedicated probation field, you can:
|
||||
- Use the notes field to record probation end date
|
||||
- Create a short-term contract for the probation period
|
||||
- Create a permanent contract after successful completion
|
||||
|
||||
### Q: What currencies are supported?
|
||||
**A:** The salary currency field accepts any 3-letter currency code (USD, EUR, GBP, etc.). Display formatting follows Dolibarr's regional settings.
|
||||
|
||||
## Payroll Management
|
||||
|
||||
### Q: Does MokoDoliHRM calculate taxes automatically?
|
||||
**A:** No, the module does not include automatic tax calculations. You must calculate taxes according to your jurisdiction's rules and enter the amounts manually.
|
||||
|
||||
### Q: Can I integrate with payroll services?
|
||||
**A:** The module doesn't have built-in integrations. You would need to:
|
||||
- Export data from MokoDoliHRM
|
||||
- Import into your payroll service
|
||||
- Or develop a custom integration using the API
|
||||
|
||||
### Q: How often should I create payroll records?
|
||||
**A:** Create payroll records according to your pay schedule (weekly, bi-weekly, monthly, etc.). Each payment period should have its own record.
|
||||
|
||||
### Q: Can I correct a payroll mistake?
|
||||
**A:**
|
||||
- If status is "Draft": Edit the record directly
|
||||
- If status is "Validated" or "Paid": Create a correction/adjustment record or set to cancelled and create a new one
|
||||
|
||||
### Q: Where is the net salary calculated?
|
||||
**A:** Net salary is not automatically calculated. You must enter it based on:
|
||||
```
|
||||
Net Salary = Gross Salary - Tax Amount - Social Security - Deductions + Bonuses
|
||||
```
|
||||
|
||||
### Q: Can I generate payslips?
|
||||
**A:** The current version doesn't include payslip generation. You can:
|
||||
- Export data and use external tools
|
||||
- Create custom reports using Dolibarr's reporting features
|
||||
- Extend the module with payslip generation functionality
|
||||
|
||||
## Permissions & Security
|
||||
|
||||
### Q: How do I control who can access HR data?
|
||||
**A:** Use Dolibarr's permission system:
|
||||
1. Go to **Home → Setup → Users & Groups**
|
||||
2. Select a user or group
|
||||
3. Configure MokoDoliHRM permissions (Read, Write, Delete for each module)
|
||||
|
||||
### Q: Can I limit access to sensitive information?
|
||||
**A:**
|
||||
- Use private notes for sensitive information
|
||||
- Grant "Read" permission only to users who need access
|
||||
- Consider custom modifications for field-level security
|
||||
|
||||
### Q: Is the data encrypted?
|
||||
**A:** Data is stored in the Dolibarr database. Encryption depends on:
|
||||
- Database configuration (enable encryption at rest)
|
||||
- HTTPS for data in transit
|
||||
- Dolibarr's security settings
|
||||
|
||||
### Q: Should I backup HR data separately?
|
||||
**A:** Yes, HR data is critical. We recommend:
|
||||
- Regular automated database backups
|
||||
- Separate backups before major changes
|
||||
- Testing restoration procedures
|
||||
- Offsite backup storage
|
||||
|
||||
## Customization & Development
|
||||
|
||||
### Q: Can I add custom fields?
|
||||
**A:** Yes, but it requires:
|
||||
1. Modifying the database schema (add columns)
|
||||
2. Updating class files to include new fields
|
||||
3. Modifying UI pages to display/edit fields
|
||||
4. Following moko-platform structure
|
||||
|
||||
### Q: How do I add new features?
|
||||
**A:**
|
||||
1. Fork the repository
|
||||
2. Add your features following the existing code structure
|
||||
3. Test thoroughly
|
||||
4. Consider contributing back to the main project
|
||||
|
||||
### Q: Can I change the look and feel?
|
||||
**A:** Yes, through:
|
||||
- Dolibarr themes (affects entire system)
|
||||
- Custom CSS in the module
|
||||
- Modifying page templates
|
||||
|
||||
### Q: Is there an API?
|
||||
**A:** The classes provide programmatic access. See [API Documentation](API.md) for details on using the PHP classes. For REST API, you'd need to extend Dolibarr's API module.
|
||||
|
||||
## Data & Reporting
|
||||
|
||||
### Q: How do I export data?
|
||||
**A:** Options include:
|
||||
- Using Dolibarr's export module
|
||||
- Direct database queries
|
||||
- Custom export scripts
|
||||
- Using the search/filter features and copying visible data
|
||||
|
||||
### Q: Can I generate reports?
|
||||
**A:**
|
||||
- Use Dolibarr's built-in reporting features
|
||||
- Export data to external tools (Excel, BI software)
|
||||
- Develop custom reports as module extensions
|
||||
|
||||
### Q: How long should I keep records?
|
||||
**A:** This depends on:
|
||||
- Legal requirements in your jurisdiction
|
||||
- Company policy
|
||||
- Type of records (employee files, payroll, contracts)
|
||||
|
||||
Consult with legal counsel for your specific requirements.
|
||||
|
||||
### Q: Can I archive old records?
|
||||
**A:** The module doesn't include an archive feature. Options:
|
||||
- Set status to "Terminated" for ended employment
|
||||
- Export old records to external storage
|
||||
- Keep all records in the database (recommended for compliance)
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Q: Why can't I see the MokoDoliHRM menu?
|
||||
**A:**
|
||||
- Module may not be activated
|
||||
- You may not have Read permission
|
||||
- Browser cache may need clearing
|
||||
|
||||
### Q: Employee list is slow to load
|
||||
**A:**
|
||||
- Use search filters to limit results
|
||||
- Check database indexes are created
|
||||
- Optimize Dolibarr database
|
||||
- Upgrade to faster hardware if needed
|
||||
|
||||
### Q: I see "Error: Permission denied"
|
||||
**A:** Your user account doesn't have the required permission. Contact your administrator to grant appropriate access.
|
||||
|
||||
### Q: Changes aren't being saved
|
||||
**A:**
|
||||
- Check for error messages
|
||||
- Verify Write permission
|
||||
- Check database connection
|
||||
- Review Dolibarr error log
|
||||
|
||||
### Q: Where are error logs located?
|
||||
**A:** Dolibarr logs are typically at: `documents/dolibarr.log`
|
||||
|
||||
## Compliance & Legal
|
||||
|
||||
### Q: Is MokoDoliHRM GDPR compliant?
|
||||
**A:** The module provides tools for HR management, but compliance depends on how you use it:
|
||||
- Implement proper access controls
|
||||
- Have data processing agreements
|
||||
- Implement right to erasure procedures
|
||||
- Maintain audit logs
|
||||
- Consult with a GDPR specialist
|
||||
|
||||
### Q: Can employees access their own data?
|
||||
**A:** Not by default. You would need to:
|
||||
- Create employee user accounts
|
||||
- Grant them limited Read permissions
|
||||
- Possibly develop an employee self-service portal
|
||||
|
||||
### Q: How do I handle data protection requests?
|
||||
**A:**
|
||||
- Right to access: Export employee's data
|
||||
- Right to rectification: Edit employee records
|
||||
- Right to erasure: Delete employee record (be aware of legal retention requirements)
|
||||
|
||||
### Q: What about tax compliance?
|
||||
**A:** The module is a record-keeping tool. You are responsible for:
|
||||
- Correct tax calculations
|
||||
- Timely tax payments
|
||||
- Compliance with local regulations
|
||||
- Proper reporting
|
||||
|
||||
Consult with tax professionals for your jurisdiction.
|
||||
|
||||
## Support & Community
|
||||
|
||||
### Q: Where can I get help?
|
||||
**A:**
|
||||
- Read the documentation (README, Installation Guide, User Guide, API docs)
|
||||
- Check this FAQ
|
||||
- Review the code comments
|
||||
- Submit issues on the project repository
|
||||
|
||||
### Q: Can I contribute to the project?
|
||||
**A:** Yes! Contributions are welcome:
|
||||
- Bug fixes
|
||||
- New features
|
||||
- Documentation improvements
|
||||
- Translations
|
||||
- Testing and feedback
|
||||
|
||||
### Q: How do I report bugs?
|
||||
**A:**
|
||||
1. Check if the issue already exists
|
||||
2. Gather information (version, error messages, steps to reproduce)
|
||||
3. Submit a detailed issue report
|
||||
4. Include screenshots if relevant
|
||||
|
||||
### Q: Are there commercial support options?
|
||||
**A:** Contact Moko Consulting for professional support, customization, and training services.
|
||||
|
||||
## Upgrading & Maintenance
|
||||
|
||||
### Q: How do I upgrade to a new version?
|
||||
**A:**
|
||||
1. Backup your database and files
|
||||
2. Deactivate the module
|
||||
3. Replace module files
|
||||
4. Reactivate the module
|
||||
5. Test thoroughly
|
||||
|
||||
### Q: Will upgrades delete my data?
|
||||
**A:** No, data remains in the database. However, always backup before upgrading.
|
||||
|
||||
### Q: How often should I update?
|
||||
**A:** Update when:
|
||||
- Security fixes are released
|
||||
- New features you need are added
|
||||
- Bug fixes address issues you're experiencing
|
||||
- Compatibility updates for Dolibarr are released
|
||||
|
||||
### Q: Can I skip versions when upgrading?
|
||||
**A:** Generally yes, but review release notes for any special upgrade procedures or breaking changes.
|
||||
|
||||
---
|
||||
|
||||
**Still have questions?** Check the [User Guide](USER_GUIDE.md) or [API Documentation](API.md) for more detailed information.
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,41 @@
|
||||
# MokoDoliHRM
|
||||
|
||||
| Field | Value |
|
||||
|---|---|
|
||||
| **License** | GPL-3.0-or-later |
|
||||
| **Platform** | [Gitea](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) |
|
||||
|
||||
---
|
||||
|
||||
## Guides
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [INSTALLATION](INSTALLATION) | ← [Home](Home) |
|
||||
|
||||
## Reference
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [API](API) | ← [Home](Home) |
|
||||
| [README](README) | ← [Home](Home) |
|
||||
|
||||
## Documentation
|
||||
|
||||
| Page | Description |
|
||||
|---|---|
|
||||
| [FAQ](FAQ) | ← [Home](Home) |
|
||||
| [USER_GUIDE](USER_GUIDE) | ← [Home](Home) |
|
||||
| [update server](update-server.-.-) | ← [Home](Home) |
|
||||
|
||||
---
|
||||
|
||||
> [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,236 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliHRM Installation Guide
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before installing MokoDoliHRM, ensure you have:
|
||||
|
||||
- Dolibarr ERP/CRM version 13.0 or higher
|
||||
- PHP version 7.0 or higher
|
||||
- MySQL or MariaDB database
|
||||
- Administrative access to your Dolibarr installation
|
||||
|
||||
## Installation Steps
|
||||
|
||||
### Method 1: Manual Installation
|
||||
|
||||
1. **Download the Module**
|
||||
- Download the MokoDoliHRM module files from the repository
|
||||
- Extract the files to a temporary location
|
||||
|
||||
2. **Copy Files to Dolibarr**
|
||||
```bash
|
||||
# Navigate to your Dolibarr installation directory
|
||||
cd /path/to/dolibarr
|
||||
|
||||
# Create the custom module directory
|
||||
mkdir -p htdocs/custom/mokodolihrm
|
||||
|
||||
# Copy the src folder contents to the module directory
|
||||
cp -r /path/to/mokoDoliHRM/src/* htdocs/custom/mokodolihrm/
|
||||
```
|
||||
|
||||
3. **Set Proper Permissions**
|
||||
```bash
|
||||
# Set ownership (adjust user:group as needed)
|
||||
chown -R www-data:www-data htdocs/custom/mokodolihrm
|
||||
|
||||
# Set directory permissions
|
||||
find htdocs/custom/mokodolihrm -type d -exec chmod 755 {} \;
|
||||
|
||||
# Set file permissions
|
||||
find htdocs/custom/mokodolihrm -type f -exec chmod 644 {} \;
|
||||
```
|
||||
|
||||
4. **Activate the Module**
|
||||
- Log in to Dolibarr as an administrator
|
||||
- Navigate to: Home → Setup → Modules/Applications
|
||||
- Search for "MokoDoliHRM" in the modules list
|
||||
- Click the "On/Off" switch to activate the module
|
||||
- The module will automatically create the required database tables
|
||||
|
||||
5. **Configure Permissions**
|
||||
- Navigate to: Home → Setup → Users & Groups
|
||||
- Select a user or group
|
||||
- Grant the appropriate MokoDoliHRM permissions:
|
||||
- Employee: Read, Write, Delete
|
||||
- Contract: Read, Write, Delete
|
||||
- Payroll: Read, Write, Delete
|
||||
|
||||
### Method 2: Using Installation Script
|
||||
|
||||
1. **Navigate to the Scripts Directory**
|
||||
```bash
|
||||
cd /path/to/mokoDoliHRM/scripts
|
||||
```
|
||||
|
||||
2. **Run the Installation Script**
|
||||
```bash
|
||||
chmod +x install.sh
|
||||
./install.sh /path/to/dolibarr
|
||||
```
|
||||
|
||||
3. **Follow On-Screen Instructions**
|
||||
- The script will copy files and set proper permissions
|
||||
- Activate the module through the Dolibarr interface as described above
|
||||
|
||||
## Post-Installation Configuration
|
||||
|
||||
### 1. Verify Installation
|
||||
|
||||
After activating the module, verify the installation:
|
||||
|
||||
- Check that the "MokoDoliHRM" menu appears in the top navigation
|
||||
- Navigate to MokoDoliHRM → Employees and ensure the page loads correctly
|
||||
- Check the database to verify that the following tables were created:
|
||||
- `llx_mokodolihrm_employee`
|
||||
- `llx_mokodolihrm_contract`
|
||||
- `llx_mokodolihrm_payroll`
|
||||
|
||||
### 2. Database Verification
|
||||
|
||||
Connect to your database and run:
|
||||
|
||||
```sql
|
||||
SHOW TABLES LIKE 'llx_mokodolihrm_%';
|
||||
```
|
||||
|
||||
You should see three tables listed.
|
||||
|
||||
### 3. Configure Module Settings
|
||||
|
||||
Navigate to: Home → Setup → Modules/Applications → MokoDoliHRM → Setup
|
||||
|
||||
Configure any module-specific settings as needed.
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Module Not Appearing in Module List
|
||||
|
||||
If the module doesn't appear in the modules list:
|
||||
|
||||
1. Clear Dolibarr cache:
|
||||
```bash
|
||||
rm -rf documents/install/locks/*.lock
|
||||
```
|
||||
|
||||
2. Verify file permissions:
|
||||
```bash
|
||||
ls -la htdocs/custom/mokodolihrm/core/modules/modMokodoliHRM/
|
||||
```
|
||||
|
||||
3. Check that `modMokodoliHRM.class.php` exists and is readable
|
||||
|
||||
### Database Tables Not Created
|
||||
|
||||
If the tables are not created automatically:
|
||||
|
||||
1. Manually run the SQL script:
|
||||
```bash
|
||||
mysql -u your_db_user -p your_db_name < src/sql/llx_mokodolihrm.sql
|
||||
```
|
||||
|
||||
2. Replace `llx_` prefix with your Dolibarr table prefix if different
|
||||
|
||||
### Permission Errors
|
||||
|
||||
If you encounter permission errors:
|
||||
|
||||
1. Verify web server user ownership:
|
||||
```bash
|
||||
ls -la htdocs/custom/mokodolihrm/
|
||||
```
|
||||
|
||||
2. Ensure the web server user (usually `www-data`, `apache`, or `nginx`) owns the files:
|
||||
```bash
|
||||
chown -R www-data:www-data htdocs/custom/mokodolihrm/
|
||||
```
|
||||
|
||||
### Module Activation Fails
|
||||
|
||||
If activation fails:
|
||||
|
||||
1. Check Dolibarr error logs:
|
||||
- Location: `documents/dolibarr.log`
|
||||
|
||||
2. Check PHP error logs:
|
||||
- Location varies by system (e.g., `/var/log/apache2/error.log`)
|
||||
|
||||
3. Ensure database user has CREATE TABLE privileges
|
||||
|
||||
## Upgrading
|
||||
|
||||
### From a Previous Version
|
||||
|
||||
1. **Backup Your Data**
|
||||
```bash
|
||||
# Backup database
|
||||
mysqldump -u user -p database_name > mokodolihrm_backup.sql
|
||||
|
||||
# Backup files
|
||||
cp -r htdocs/custom/mokodolihrm htdocs/custom/mokodolihrm.backup
|
||||
```
|
||||
|
||||
2. **Deactivate the Module**
|
||||
- Navigate to: Home → Setup → Modules/Applications
|
||||
- Deactivate MokoDoliHRM
|
||||
|
||||
3. **Replace Files**
|
||||
```bash
|
||||
rm -rf htdocs/custom/mokodolihrm/*
|
||||
cp -r /path/to/new/version/src/* htdocs/custom/mokodolihrm/
|
||||
```
|
||||
|
||||
4. **Reactivate the Module**
|
||||
- Navigate to: Home → Setup → Modules/Applications
|
||||
- Activate MokoDoliHRM
|
||||
- Any database schema updates will be applied automatically
|
||||
|
||||
## Uninstallation
|
||||
|
||||
To completely remove the module:
|
||||
|
||||
1. **Deactivate the Module**
|
||||
- Navigate to: Home → Setup → Modules/Applications
|
||||
- Deactivate MokoDoliHRM
|
||||
|
||||
2. **Remove Files**
|
||||
```bash
|
||||
rm -rf htdocs/custom/mokodolihrm
|
||||
```
|
||||
|
||||
3. **Remove Database Tables (Optional)**
|
||||
|
||||
⚠️ **Warning**: This will permanently delete all employee, contract, and payroll data.
|
||||
|
||||
```sql
|
||||
DROP TABLE IF EXISTS llx_mokodolihrm_payroll;
|
||||
DROP TABLE IF EXISTS llx_mokodolihrm_contract;
|
||||
DROP TABLE IF EXISTS llx_mokodolihrm_employee;
|
||||
```
|
||||
|
||||
## Support
|
||||
|
||||
For installation issues or questions:
|
||||
|
||||
- Check the documentation in the `docs/` folder
|
||||
- Review the FAQ in `docs/FAQ.md`
|
||||
- Submit an issue on the project repository
|
||||
|
||||
## Next Steps
|
||||
|
||||
After successful installation:
|
||||
|
||||
1. Read the user guide: `docs/USER_GUIDE.md`
|
||||
2. Configure user permissions
|
||||
3. Start adding employee records
|
||||
4. Explore contract and payroll management features
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,167 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliHRM - Employee, Contract and Payroll Management for Dolibarr
|
||||
|
||||
## Overview
|
||||
|
||||
MokoDoliHRM is a comprehensive Human Resources Management module for Dolibarr ERP/CRM that provides complete functionality for managing employees, employment contracts, and payroll processing.
|
||||
|
||||
## Features
|
||||
|
||||
### Employee Management
|
||||
- Create and manage employee records with complete personal information
|
||||
- Track employee status (Draft, Active, Terminated)
|
||||
- Store employee contact details, addresses, and identification information
|
||||
- Record hire dates, termination dates, positions, and departments
|
||||
- Manage social security numbers and bank account information
|
||||
- Add public and private notes to employee records
|
||||
|
||||
### Employee Contract Management
|
||||
- Create and manage employment contracts for each employee
|
||||
- Support multiple contract types (Permanent, Temporary, Consultant, Intern)
|
||||
- Define contract periods with start and end dates
|
||||
- Manage salary information with currency and payment period
|
||||
- Track working hours and annual leave entitlements
|
||||
- Monitor contract status throughout its lifecycle
|
||||
|
||||
### Payroll Management
|
||||
- Generate and manage payroll records for employees
|
||||
- Track payroll periods with start and end dates
|
||||
- Calculate gross salary, net salary, taxes, and social security contributions
|
||||
- Manage bonuses and deductions
|
||||
- Record payment dates and payment methods
|
||||
- Support multiple payroll statuses (Draft, Validated, Paid, Cancelled)
|
||||
|
||||
## Module Structure
|
||||
|
||||
Following moko-platform, the module is organized into the following folders:
|
||||
|
||||
```
|
||||
mokoDoliHRM/
|
||||
├── docs/ # Documentation files
|
||||
├── scripts/ # Installation and utility scripts
|
||||
├── tests/ # Test files
|
||||
└── src/ # Source code
|
||||
├── class/ # PHP classes for business logic
|
||||
├── core/ # Core module files
|
||||
│ └── modules/
|
||||
│ └── modMokodoliHRM/
|
||||
├── lang/ # Language translation files
|
||||
├── pages/ # User interface pages
|
||||
│ ├── employee/
|
||||
│ ├── contract/
|
||||
│ └── payroll/
|
||||
└── sql/ # Database schema files
|
||||
```
|
||||
|
||||
## Installation
|
||||
|
||||
1. Copy the `src` folder contents to your Dolibarr `custom/mokodolihrm/` directory
|
||||
2. Log in to Dolibarr as an administrator
|
||||
3. Navigate to Home → Setup → Modules/Applications
|
||||
4. Find "MokoDoliHRM" in the list of modules
|
||||
5. Click the "Activate" button to enable the module
|
||||
6. The module will automatically create the required database tables
|
||||
|
||||
## Usage
|
||||
|
||||
### Managing Employees
|
||||
|
||||
1. Navigate to MokoDoliHRM → Employees from the main menu
|
||||
2. Click "New Employee" to create a new employee record
|
||||
3. Fill in the required information (First Name, Last Name)
|
||||
4. Add optional details such as contact information, position, department, etc.
|
||||
5. Save the employee record
|
||||
|
||||
### Managing Contracts
|
||||
|
||||
1. Navigate to MokoDoliHRM → Contracts
|
||||
2. Click "New Contract" to create a new employment contract
|
||||
3. Select the employee for whom the contract is being created
|
||||
4. Choose the contract type and define the contract period
|
||||
5. Enter salary information and working conditions
|
||||
6. Save the contract
|
||||
|
||||
### Managing Payroll
|
||||
|
||||
1. Navigate to MokoDoliHRM → Payroll
|
||||
2. Click "New Payroll" to create a new payroll record
|
||||
3. Select the employee and optionally link to a contract
|
||||
4. Define the payroll period (start and end dates)
|
||||
5. Enter gross salary and calculate deductions (taxes, social security)
|
||||
6. Add any bonuses or additional deductions
|
||||
7. Record the payment date and method
|
||||
8. Save the payroll record
|
||||
|
||||
## Permissions
|
||||
|
||||
The module includes granular permissions for each area:
|
||||
|
||||
### Employee Permissions
|
||||
- Read employees
|
||||
- Create/Update employees
|
||||
- Delete employees
|
||||
|
||||
### Contract Permissions
|
||||
- Read contracts
|
||||
- Create/Update contracts
|
||||
- Delete contracts
|
||||
|
||||
### Payroll Permissions
|
||||
- Read payroll
|
||||
- Create/Update payroll
|
||||
- Delete payroll
|
||||
|
||||
Permissions can be configured per user or user group in Dolibarr's user management interface.
|
||||
|
||||
## Database Schema
|
||||
|
||||
The module creates three main tables:
|
||||
|
||||
### llx_mokodolihrm_employee
|
||||
Stores employee information including personal details, contact information, position, and status.
|
||||
|
||||
### llx_mokodolihrm_contract
|
||||
Stores employment contract information linked to employees, including contract type, dates, salary, and working conditions.
|
||||
|
||||
### llx_mokodolihrm_payroll
|
||||
Stores payroll records linked to employees and optionally to contracts, including salary calculations, taxes, and payment information.
|
||||
|
||||
## Technical Details
|
||||
|
||||
### Module Information
|
||||
- **Module Number**: 185060
|
||||
- **Module Machine Name**: `mokodolihrm` (folder, DB prefix, conf key, permission key, `$this->name`)
|
||||
- **Module Family**: HR (Human Resources)
|
||||
- **Version**: 1.0.0
|
||||
- **Minimum PHP Version**: 7.0
|
||||
- **Minimum Dolibarr Version**: 13.0
|
||||
|
||||
### Classes
|
||||
|
||||
#### MokoEmployee
|
||||
Main class for employee management with CRUD operations.
|
||||
|
||||
#### MokoContract
|
||||
Class for managing employment contracts with relationships to employees.
|
||||
|
||||
#### MokoPayroll
|
||||
Class for payroll processing with relationships to employees and contracts.
|
||||
|
||||
## Support and Contribution
|
||||
|
||||
For issues, questions, or contributions, please refer to the project repository.
|
||||
|
||||
## License
|
||||
|
||||
This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
|
||||
|
||||
Copyright (C) 2024 Moko Consulting
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,412 @@
|
||||
← [Home](Home)
|
||||
|
||||
# MokoDoliHRM User Guide
|
||||
|
||||
## Table of Contents
|
||||
1. [Introduction](#introduction)
|
||||
2. [Getting Started](#getting-started)
|
||||
3. [Employee Management](#employee-management)
|
||||
4. [Contract Management](#contract-management)
|
||||
5. [Payroll Management](#payroll-management)
|
||||
6. [Best Practices](#best-practices)
|
||||
7. [Troubleshooting](#troubleshooting)
|
||||
|
||||
## Introduction
|
||||
|
||||
MokoDoliHRM is a comprehensive HR management module for Dolibarr that helps you manage your workforce efficiently. This guide will walk you through all the features and show you how to make the most of the module.
|
||||
|
||||
### Key Features
|
||||
|
||||
- **Employee Database**: Maintain complete employee records with personal and professional information
|
||||
- **Contract Management**: Track employment contracts with detailed terms and conditions
|
||||
- **Payroll Processing**: Process and track employee compensation and deductions
|
||||
|
||||
## Getting Started
|
||||
|
||||
### Accessing MokoDoliHRM
|
||||
|
||||
After installation and activation:
|
||||
|
||||
1. Log in to Dolibarr
|
||||
2. Look for the "MokoDoliHRM" menu in the top navigation bar
|
||||
3. Click on it to access the main menu with three sections:
|
||||
- Employees
|
||||
- Contracts
|
||||
- Payroll
|
||||
|
||||
### User Permissions
|
||||
|
||||
Before using MokoDoliHRM, ensure you have the appropriate permissions:
|
||||
|
||||
- **Read**: View employee, contract, and payroll records
|
||||
- **Write**: Create and modify records
|
||||
- **Delete**: Remove records from the system
|
||||
|
||||
Administrators can configure these permissions in: **Home → Setup → Users & Groups**
|
||||
|
||||
## Employee Management
|
||||
|
||||
### Creating a New Employee
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Employees**
|
||||
2. Click the **New Employee** button
|
||||
3. Fill in the required information:
|
||||
- **First Name** (required)
|
||||
- **Last Name** (required)
|
||||
- Email
|
||||
- Phone
|
||||
- Position
|
||||
- Department
|
||||
- Hire Date
|
||||
- Status (Draft or Active)
|
||||
4. Click **Create** to save the employee record
|
||||
|
||||
### Employee Information Fields
|
||||
|
||||
#### Personal Information
|
||||
- **First Name & Last Name**: Employee's legal name
|
||||
- **Date of Birth**: Used for age calculations and legal compliance
|
||||
- **Address, City, Zip**: Residential address
|
||||
- **Country**: Select from country list
|
||||
|
||||
#### Contact Information
|
||||
- **Email**: Primary email address for communication
|
||||
- **Phone**: Primary contact number
|
||||
|
||||
#### Employment Information
|
||||
- **Reference**: Auto-generated employee ID (e.g., EMP00001)
|
||||
- **Position**: Job title or role
|
||||
- **Department**: Organizational unit
|
||||
- **Hire Date**: Employment start date
|
||||
- **Termination Date**: Set when employment ends
|
||||
|
||||
#### Financial Information
|
||||
- **Social Security Number**: For tax and benefits administration
|
||||
- **Bank Account**: For direct deposit payments
|
||||
|
||||
#### Notes
|
||||
- **Public Notes**: Visible to users with read permission
|
||||
- **Private Notes**: Visible only to users with elevated permissions
|
||||
|
||||
### Viewing Employee Records
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Employees**
|
||||
2. The list displays all employees with:
|
||||
- Employee reference
|
||||
- Name
|
||||
- Position
|
||||
- Department
|
||||
- Status
|
||||
3. Click on any employee reference to view full details
|
||||
|
||||
### Searching and Filtering
|
||||
|
||||
Use the search fields at the top of the employee list:
|
||||
- **Reference**: Search by employee ID
|
||||
- **First Name**: Filter by first name
|
||||
- **Last Name**: Filter by last name
|
||||
- **Position**: Filter by job title
|
||||
- **Department**: Filter by department
|
||||
- **Status**: Filter by employment status
|
||||
|
||||
Click the **Search** button to apply filters.
|
||||
|
||||
### Editing Employee Information
|
||||
|
||||
1. Open the employee record
|
||||
2. Click the **Modify** button
|
||||
3. Update the necessary fields
|
||||
4. Click **Save** to commit changes
|
||||
|
||||
### Managing Employee Status
|
||||
|
||||
Employees can have three statuses:
|
||||
|
||||
- **Draft (0)**: Preliminary record, not yet active
|
||||
- **Active (1)**: Currently employed
|
||||
- **Terminated (9)**: Employment ended
|
||||
|
||||
To change status:
|
||||
1. Edit the employee record
|
||||
2. Select the new status from the dropdown
|
||||
3. If terminating, set the termination date
|
||||
4. Save the changes
|
||||
|
||||
### Deleting Employees
|
||||
|
||||
⚠️ **Warning**: Deleting an employee will also delete all associated contracts and payroll records due to database constraints.
|
||||
|
||||
1. Open the employee record
|
||||
2. Click the **Delete** button
|
||||
3. Confirm the deletion
|
||||
4. The employee and all related data will be removed
|
||||
|
||||
## Contract Management
|
||||
|
||||
### Understanding Employment Contracts
|
||||
|
||||
Contracts define the terms of employment including:
|
||||
- Contract type and duration
|
||||
- Compensation details
|
||||
- Working conditions
|
||||
- Leave entitlements
|
||||
|
||||
### Creating a New Contract
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Contracts**
|
||||
2. Click the **New Contract** button
|
||||
3. Select the employee
|
||||
4. Fill in contract details:
|
||||
- **Contract Type**: Permanent, Temporary, Consultant, or Intern
|
||||
- **Start Date**: When the contract begins
|
||||
- **End Date**: When the contract ends (if applicable)
|
||||
- **Salary**: Compensation amount
|
||||
- **Currency**: Payment currency
|
||||
- **Salary Period**: Monthly, Weekly, or Hourly
|
||||
- **Working Hours**: Hours per week
|
||||
- **Annual Leave Days**: Vacation entitlement
|
||||
5. Click **Create** to save
|
||||
|
||||
### Contract Types
|
||||
|
||||
- **Permanent**: Ongoing employment with no fixed end date
|
||||
- **Temporary**: Fixed-term employment
|
||||
- **Consultant**: Contract-based engagement
|
||||
- **Intern**: Training or educational placement
|
||||
|
||||
### Salary Configuration
|
||||
|
||||
When setting up salary information:
|
||||
1. Enter the gross salary amount
|
||||
2. Select the appropriate currency (USD, EUR, etc.)
|
||||
3. Specify the payment period:
|
||||
- **Monthly**: Salary paid once per month
|
||||
- **Weekly**: Salary paid weekly
|
||||
- **Hourly**: Compensation per hour worked
|
||||
|
||||
### Viewing Contracts
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Contracts**
|
||||
2. The list shows:
|
||||
- Contract reference
|
||||
- Employee name
|
||||
- Contract type
|
||||
- Start date
|
||||
- Salary
|
||||
- Status
|
||||
3. Click on a contract reference for full details
|
||||
|
||||
### Contract Status Management
|
||||
|
||||
Contracts follow the same status workflow as employees:
|
||||
- **Draft**: Being prepared
|
||||
- **Active**: Currently in effect
|
||||
- **Terminated**: Ended
|
||||
|
||||
### Modifying Contracts
|
||||
|
||||
To update contract terms:
|
||||
1. Open the contract record
|
||||
2. Click **Modify**
|
||||
3. Update the necessary fields
|
||||
4. Save changes
|
||||
|
||||
**Best Practice**: When salary or terms change significantly, consider creating a new contract rather than modifying the existing one to maintain historical records.
|
||||
|
||||
## Payroll Management
|
||||
|
||||
### Overview
|
||||
|
||||
The payroll module helps you track employee compensation, calculate deductions, and maintain payment records.
|
||||
|
||||
### Creating a Payroll Record
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Payroll**
|
||||
2. Click **New Payroll**
|
||||
3. Fill in the payroll details:
|
||||
- **Employee**: Select from the list
|
||||
- **Contract**: Optionally link to a specific contract
|
||||
- **Period Start**: Beginning of pay period
|
||||
- **Period End**: End of pay period
|
||||
- **Gross Salary**: Total compensation before deductions
|
||||
- **Tax Amount**: Income tax withheld
|
||||
- **Social Security**: Social security contributions
|
||||
- **Bonuses**: Additional compensation
|
||||
- **Deductions**: Other deductions
|
||||
- **Net Salary**: Final amount paid (calculated or entered)
|
||||
- **Payment Date**: When payment was/will be made
|
||||
- **Payment Method**: Bank Transfer, Cash, or Check
|
||||
4. Set the status (Draft, Validated, or Paid)
|
||||
5. Click **Create**
|
||||
|
||||
### Payroll Calculation
|
||||
|
||||
While the module doesn't automatically calculate taxes, you can:
|
||||
|
||||
1. Calculate externally or using your country's tax rules
|
||||
2. Enter the calculated values into the fields
|
||||
3. The net salary is: Gross Salary - Tax - Social Security - Deductions + Bonuses
|
||||
|
||||
**Formula**:
|
||||
```
|
||||
Net Salary = Gross Salary - Tax Amount - Social Security - Deductions + Bonuses
|
||||
```
|
||||
|
||||
### Payroll Status Workflow
|
||||
|
||||
1. **Draft (0)**: Payroll being prepared
|
||||
2. **Validated (1)**: Payroll approved and ready for payment
|
||||
3. **Paid (2)**: Payment has been made
|
||||
4. **Cancelled (9)**: Payroll voided
|
||||
|
||||
### Viewing Payroll Records
|
||||
|
||||
1. Navigate to **MokoDoliHRM → Payroll**
|
||||
2. The list displays:
|
||||
- Payroll reference
|
||||
- Employee name
|
||||
- Pay period dates
|
||||
- Net salary
|
||||
- Status
|
||||
3. Click on a reference to view full details
|
||||
|
||||
### Reporting on Payroll
|
||||
|
||||
To extract payroll data:
|
||||
1. Use the search and filter features
|
||||
2. Filter by employee, date range, or status
|
||||
3. Export data for external reporting tools
|
||||
|
||||
## Best Practices
|
||||
|
||||
### Employee Management
|
||||
|
||||
1. **Complete Records**: Fill in as much information as possible for each employee
|
||||
2. **Regular Updates**: Keep contact information and positions current
|
||||
3. **Status Management**: Always update status when employment circumstances change
|
||||
4. **Documentation**: Use notes fields to record important events or information
|
||||
|
||||
### Contract Management
|
||||
|
||||
1. **Create Contracts Immediately**: Set up contracts when employees are hired
|
||||
2. **Document Changes**: Create new contracts for significant changes (promotions, role changes)
|
||||
3. **Track End Dates**: Monitor temporary contracts and renew or terminate as needed
|
||||
4. **Salary Reviews**: Update contracts during annual reviews or compensation changes
|
||||
|
||||
### Payroll Processing
|
||||
|
||||
1. **Consistent Timing**: Process payroll on the same schedule each period
|
||||
2. **Verify Calculations**: Double-check tax and deduction calculations
|
||||
3. **Link to Contracts**: Associate payroll with contracts for better tracking
|
||||
4. **Status Progression**: Move through statuses systematically (Draft → Validated → Paid)
|
||||
5. **Backup Records**: Maintain external backups of payroll data for compliance
|
||||
|
||||
### Data Security
|
||||
|
||||
1. **Access Control**: Grant permissions based on job requirements
|
||||
2. **Private Information**: Use private notes for sensitive information
|
||||
3. **Regular Audits**: Review who has access to HR data
|
||||
4. **Backup**: Regularly backup your Dolibarr database
|
||||
|
||||
## Troubleshooting
|
||||
|
||||
### Common Issues
|
||||
|
||||
#### Cannot See MokoDoliHRM Menu
|
||||
|
||||
**Solution**:
|
||||
- Verify the module is activated: **Home → Setup → Modules**
|
||||
- Check your user permissions
|
||||
- Clear browser cache and reload
|
||||
|
||||
#### Cannot Create Employees
|
||||
|
||||
**Solution**:
|
||||
- Verify you have "Write" permission for employees
|
||||
- Check that required fields (First Name, Last Name) are filled
|
||||
- Review error messages for specific issues
|
||||
|
||||
#### Database Errors
|
||||
|
||||
**Solution**:
|
||||
- Ensure the database tables were created during installation
|
||||
- Check that your database user has appropriate privileges
|
||||
- Review Dolibarr error logs: `documents/dolibarr.log`
|
||||
|
||||
#### Salary Not Displaying Correctly
|
||||
|
||||
**Solution**:
|
||||
- Verify the currency is set correctly
|
||||
- Check regional settings in Dolibarr
|
||||
- Ensure numeric values don't contain invalid characters
|
||||
|
||||
### Getting Help
|
||||
|
||||
If you encounter issues not covered here:
|
||||
|
||||
1. Check the API documentation: `docs/API.md`
|
||||
2. Review installation guide: `docs/INSTALLATION.md`
|
||||
3. Check Dolibarr logs for error details
|
||||
4. Verify your Dolibarr version meets minimum requirements (13.0+)
|
||||
|
||||
### Performance Tips
|
||||
|
||||
For large employee databases:
|
||||
|
||||
1. Use filters effectively to limit result sets
|
||||
2. Archive terminated employees rather than deleting them
|
||||
3. Regular database maintenance and optimization
|
||||
4. Consider pagination when viewing large lists
|
||||
|
||||
## Appendix
|
||||
|
||||
### Keyboard Shortcuts
|
||||
|
||||
- **Tab**: Navigate between form fields
|
||||
- **Enter**: Submit forms (when focused on a button)
|
||||
- **Esc**: Close modals or cancel operations
|
||||
|
||||
### Module Settings
|
||||
|
||||
Access module configuration:
|
||||
**Home → Setup → Modules → MokoDoliHRM → Setup**
|
||||
|
||||
Available settings:
|
||||
- Default Annual Leave Days
|
||||
- Default Working Hours
|
||||
|
||||
### Data Export
|
||||
|
||||
While MokoDoliHRM doesn't include built-in export features, you can:
|
||||
|
||||
1. Use Dolibarr's export module for standard exports
|
||||
2. Query the database directly:
|
||||
- `llx_mokodolihrm_employee`
|
||||
- `llx_mokodolihrm_contract`
|
||||
- `llx_mokodolihrm_payroll`
|
||||
3. Use the API to extract data programmatically
|
||||
|
||||
### Legal Compliance
|
||||
|
||||
**Important**: This module is a tool for managing HR data. You are responsible for ensuring compliance with:
|
||||
|
||||
- Local labor laws
|
||||
- Tax regulations
|
||||
- Data protection requirements (GDPR, etc.)
|
||||
- Record retention policies
|
||||
|
||||
Consult with legal and HR professionals to ensure proper usage.
|
||||
|
||||
---
|
||||
|
||||
**Version**: 1.0.0
|
||||
**Last Updated**: 2024
|
||||
**Copyright**: Moko Consulting
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
@@ -0,0 +1,64 @@
|
||||
← [Home](Home)
|
||||
|
||||
# Dolibarr Update Server
|
||||
|
||||
[](https://git.mokoconsulting.tech/MokoConsulting/moko-platform)
|
||||
|
||||
This document explains how `update.txt` is automatically managed for this Dolibarr module.
|
||||
|
||||
## How It Works
|
||||
|
||||
Dolibarr checks for module updates by fetching a plain-text file from the URL in `$this->url_last_version` in the module descriptor (`src/core/modules/mod*.class.php`). The file must contain **only the version string** — no JSON, no XML, no trailing newline.
|
||||
|
||||
### Automatic Generation
|
||||
|
||||
| Event | Workflow | `update.txt` Content | `$this->version` |
|
||||
|-------|----------|---------------------|-------------------|
|
||||
| Merge to `main` | `auto-release.yml` | `XX.YY.ZZ` (real version) | Real version |
|
||||
| Push to `dev/**` | `deploy-dev.yml` | `development` | `development` |
|
||||
| Push to `rc/**` | `deploy-dev.yml` | `XX.YY.ZZ-rc` | RC version |
|
||||
|
||||
### Module Descriptor
|
||||
|
||||
The `url_last_version` in your module descriptor should point to:
|
||||
|
||||
```
|
||||
https://raw.githubusercontent.com/mokoconsulting-tech/MokoDoliHRM/main/update.txt
|
||||
```
|
||||
|
||||
This is set automatically by `version_set_platform.php` during the build pipeline. **Never manually edit `$this->version` or `$this->url_last_version`** — the workflows handle it.
|
||||
|
||||
### Branch Lifecycle
|
||||
|
||||
```
|
||||
dev/XX.YY.ZZ → rc/XX.YY.ZZ → main → version/XX
|
||||
(development) (release candidate) (stable release) (frozen snapshot)
|
||||
```
|
||||
|
||||
1. **Development** (`dev/**`): `update.txt` = `development`, `$this->version` = `development`
|
||||
2. **Release Candidate** (`rc/**`): `update.txt` = `XX.YY.ZZ-rc`, version set to RC
|
||||
3. **Stable Release** (merge to `main`): `auto-release.yml` writes real version to `update.txt`, creates GitHub Release + tag, creates `version/XX` branch
|
||||
4. **Frozen Snapshot** (`version/XX`): immutable, never force-pushed
|
||||
|
||||
### Health Checks
|
||||
|
||||
The `repo_health.yml` workflow verifies on every commit:
|
||||
|
||||
- `update.txt` exists in the repository root
|
||||
- Module descriptor (`mod*.class.php`) exists in `src/core/modules/`
|
||||
- `$this->numero` is set and non-zero
|
||||
- `$this->version` is not hardcoded (should be set by workflow)
|
||||
- `url_last_version` points to `update.txt` (not `update.json`)
|
||||
- `url_last_version` references `/main/` branch on the main branch
|
||||
|
||||
---
|
||||
|
||||
*Managed by [moko-platform](https://git.mokoconsulting.tech/MokoConsulting/moko-platform). See [docs/workflows/update-server.md](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/blob/main/docs/workflows/update-server.md) for the full specification.*
|
||||
|
||||
---
|
||||
|
||||
*Repo: [MokoDoliHRM](https://git.mokoconsulting.tech/MokoConsulting/MokoDoliHRM) · [MokoStandards](https://git.mokoconsulting.tech/MokoConsulting/moko-platform/wiki/Home)*
|
||||
|
||||
| Revision | Date | Author | Description |
|
||||
|---|---|---|---|
|
||||
| 1.0 | 2026-05-09 | Moko Consulting | Initial version |
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user