add tests for caldav_sync, new module preamble_on_quotation

This commit is contained in:
Marc Durepos 2025-04-22 10:01:12 -04:00
parent a0e5d8664d
commit a76182dcd4
12 changed files with 3524 additions and 0 deletions

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,45 @@
BEGIN:VCALENDAR
PRODID:-//Apple Inc.//macOS 15.3.2//EN
VERSION:2.0
METHOD:REQUEST
CALSCALE:GREGORIAN
BEGIN:VTIMEZONE
TZID:America/Toronto
BEGIN:DAYLIGHT
DTSTART:20070311T020000
RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=2SU
TZNAME:EDT
TZOFFSETFROM:-0500
TZOFFSETTO:-0400
END:DAYLIGHT
BEGIN:STANDARD
DTSTART:20071104T020000
RRULE:FREQ=YEARLY;BYMONTH=11;BYDAY=1SU
TZNAME:EST
TZOFFSETFROM:-0400
TZOFFSETTO:-0500
END:STANDARD
END:VTIMEZONE
BEGIN:VEVENT
CREATED:20250410T122458Z
DTEND;TZID=America/Toronto:20250414T140000
DTSTAMP:20250410T122459Z
DTSTART;TZID=America/Toronto:20250414T131500
LAST-MODIFIED:20250410T122458Z
SEQUENCE:0
SUMMARY:Test
TRANSP:OPAQUE
UID:02EEF1D6-F3D2-4EB2-AD7A-1C381A629DC5
X-APPLE-CREATOR-IDENTITY:com.apple.calendar
X-APPLE-CREATOR-TEAM-IDENTITY:0000000000
BEGIN:VALARM
ACTION:NONE
TRIGGER;VALUE=DATE-TIME:19760401T005545Z
END:VALARM
ATTENDEE;PARTSTAT=NEEDS-ACTION;EMAIL=mdurepos@durpro.com;CN=Marc Durepos;CU
TYPE=INDIVIDUAL;RSVP=TRUE:mailto:mdurepos@durpro.com
ORGANIZER;CN=Marc Durepos;EMAIL=deploy@bemade.org:mailto:marc@bemade.org
CLASS:PUBLIC
END:VEVENT
END:VCALENDAR

View file

@ -0,0 +1,14 @@
BEGIN:VCALENDAR
VERSION:2.0
PRODID:-//Odoo//CalDAV Client//EN
BEGIN:VEVENT
UID:external-organizer-test-123
DTSTART:20250207T143000Z
DTEND:20250207T153000Z
DTSTAMP:20250207T143000Z
ATTENDEE;PARTSTAT=ACCEPTED;CN=Test User:mailto:test@example.com
ATTENDEE;PARTSTAT=ACCEPTED;CN=Mister External:mailto:mister.external@otherdomain.com
SUMMARY:Meeting with External Organizer
DESCRIPTION:This is a test event with an external organizer
END:VEVENT
END:VCALENDAR

View file

@ -53,3 +53,29 @@ class TestExternalOrganizer(TransactionCase, CaldavTestCommon):
external_attendee,
"External organizer should be present in attendees list",
)
def test_no_organizer_external_event_sync(self):
"""Test that events without organizers are assigned to the calendar's user."""
# Setup mock for CalDAV client with our test ICS file
with _patch_caldav_with_events_from_ics(
[_get_ics_path("test_external_no_organizer.ics")], self.user
):
self.user._compute_is_caldav_enabled()
# Make sure that the current user is not the admin user
self.assertNotEqual(self.user.id, self.env.ref("base.user_admin").id)
self.env["calendar.event"].poll_caldav_server()
# Find the synced event
event = self.env["calendar.event"].search(
[("caldav_uid", "=", "external-organizer-test-123")]
)
# Verify event was created
self.assertTrue(event, "Event should be created")
# Verify user_id is set to the calendar's user
self.assertEqual(
event.user_id,
self.user,
"Event without organizer should have user_id set to calendar's user",
)

View file

@ -0,0 +1 @@
from . import models

View file

@ -0,0 +1,44 @@
# Bemade Inc.
#
# Copyright (C) 2025-April Bemade Inc. (<https://www.bemade.org>).
# Author: Marc Durepos (Contact : mdurepos@durpro.com)
#
# This program is under the terms of the GNU Lesser General Public License (LGPL-3)
# For details, visit https://www.gnu.org/licenses/lgpl-3.0.en.html
{
"name": "Quotation PDF Preamble",
"version": "18.0.0.1.0",
"license": "LGPL-3",
"category": "Sales",
"summary": "Add customizable HTML preamble to quotation PDFs",
"author": "Bemade Inc.",
"website": "https://www.bemade.org",
"depends": ["base", "sale"],
"data": [
"views/sale_order_views.xml",
"report/sale_report_templates.xml",
"views/res_company_views.xml",
],
"description": """
Quotation PDF Preamble
======================
This module enhances the standard quotation PDF reports by allowing users to add a
customizable HTML preamble at the beginning of the document. The preamble appears
before the quotation details, similar to how the terms and conditions appear after.
Features:
---------
* Add a configurable HTML preamble field to sales orders
* Display the preamble at the top of quotation PDF reports
* Company-specific default preambles that can be overridden per quotation
* Uses Odoo's standard HTML field type for content editing
This module is ideal for businesses that need to include standard disclaimers,
terms and conditions, or promotional content at the beginning of their quotations.
""",
"installable": True,
"application": False,
"auto_install": False,
}

View file

@ -0,0 +1,2 @@
from . import sale_order
from . import res_company

View file

@ -0,0 +1,12 @@
from odoo import fields, models
class ResCompany(models.Model):
_inherit = "res.company"
default_quotation_preamble = fields.Html(
string="Default Quotation Preamble",
help="Default HTML content to display at the beginning of quotation PDFs",
sanitize=True,
sanitize_tags=True,
)

View file

@ -0,0 +1,21 @@
from odoo import api, fields, models
class SaleOrder(models.Model):
_inherit = "sale.order"
preamble = fields.Html(
string="Quotation Preamble",
help="HTML content to display at the beginning of the quotation PDF",
sanitize=True,
sanitize_tags=True,
)
@api.model_create_multi
def create(self, vals_list):
"""Set default preamble from company settings when creating a new sale order."""
record = super().create(vals_list)
for record in self:
if not record.preamble and record.company_id.default_quotation_preamble:
record.preamble = record.company_id.default_quotation_preamble
return record

View file

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<odoo>
<!-- This template adds the preamble as a cover page before the main document -->
<template id="report_saleorder_document_preamble" inherit_id="sale.report_saleorder_document">
<xpath expr="//t[@t-call='web.external_layout']" position="before">
<t t-if="doc.preamble and doc.state in ['draft', 'sent']">
<div class="article" style="page-break-after: always;">
<div class="mt-4 mb-4">
<span t-field="doc.preamble"/>
</div>
</div>
</t>
</xpath>
</template>
</odoo>

View file

@ -0,0 +1,17 @@
<?xml version="1.0" encoding="utf-8"?>
<odoo>
<record id="view_company_form_inherit_preamble" model="ir.ui.view">
<field name="name">res.company.form.inherit.preamble</field>
<field name="model">res.company</field>
<field name="inherit_id" ref="base.view_company_form"/>
<field name="arch" type="xml">
<xpath expr="//notebook" position="inside">
<page string="Quotation Preamble" name="quotation_preamble">
<group>
<field name="default_quotation_preamble" nolabel="1" placeholder="Set a default HTML preamble for all quotations..."/>
</group>
</page>
</xpath>
</field>
</record>
</odoo>

View file

@ -0,0 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<odoo>
<record id="view_order_form_inherit_preamble" model="ir.ui.view">
<field name="name">sale.order.form.inherit.preamble</field>
<field name="model">sale.order</field>
<field name="inherit_id" ref="sale.view_order_form"/>
<field name="arch" type="xml">
<xpath expr="//page[@name='other_information']" position="after">
<page string="Quotation Preamble" name="quotation_preamble">
<field name="preamble" nolabel="1" placeholder="Add an HTML preamble to be displayed at the top of the quotation PDF..."/>
</page>
</xpath>
</field>
</record>
</odoo>