246 lines
13 KiB
XML
246 lines
13 KiB
XML
<?xml version="1.0" encoding="utf-8"?>
|
|
<odoo>
|
|
|
|
<!-- Batch List View -->
|
|
<record id="otk_seo_content_batch_view_list" model="ir.ui.view">
|
|
<field name="name">otk.seo.content.batch.list</field>
|
|
<field name="model">otk.seo.content.batch</field>
|
|
<field name="arch" type="xml">
|
|
<list string="Batch Jobs" decoration-info="state == 'draft'"
|
|
decoration-warning="state == 'processing'"
|
|
decoration-success="state == 'done'"
|
|
decoration-danger="state == 'failed'">
|
|
<field name="name"/>
|
|
<field name="source_type"/>
|
|
<field name="content_type"/>
|
|
<field name="total_items"/>
|
|
<field name="completed_items"/>
|
|
<field name="failed_items"/>
|
|
<field name="progress_percent" widget="progressbar"/>
|
|
<field name="state" widget="badge"
|
|
decoration-info="state == 'draft'"
|
|
decoration-warning="state in ('queued', 'processing')"
|
|
decoration-success="state == 'done'"
|
|
decoration-danger="state == 'failed'"/>
|
|
<field name="create_date" optional="hide"/>
|
|
</list>
|
|
</field>
|
|
</record>
|
|
|
|
<!-- Batch Form View -->
|
|
<record id="otk_seo_content_batch_view_form" model="ir.ui.view">
|
|
<field name="name">otk.seo.content.batch.form</field>
|
|
<field name="model">otk.seo.content.batch</field>
|
|
<field name="arch" type="xml">
|
|
<form string="Batch Content Generation">
|
|
<header>
|
|
<button name="action_prepare_items" string="Add Items from Source"
|
|
type="object" class="btn-secondary" icon="fa-plus"
|
|
invisible="state != 'draft' or not source_type"
|
|
help="Add items from the selected source (products, CSV, or keywords). Existing items are preserved."/>
|
|
<button name="action_clear_items" string="Clear All Items"
|
|
type="object" class="btn-secondary" icon="fa-trash"
|
|
invisible="state != 'draft' or total_items == 0"
|
|
confirm="This will remove all items from the batch. Continue?"
|
|
help="Remove all items from the batch to start fresh."/>
|
|
<button name="action_start_batch" string="Start Generation"
|
|
type="object" class="btn-primary"
|
|
invisible="state != 'draft' or total_items == 0"
|
|
confirm="This will start generating content for all items. Continue?"
|
|
help="Start generating content for all prepared items. Items will be processed one by one."/>
|
|
<button name="action_pause" string="Pause"
|
|
type="object" class="btn-secondary" icon="fa-pause"
|
|
invisible="state not in ('queued', 'processing')"
|
|
help="Pause batch processing. Items currently in progress will finish."/>
|
|
<button name="action_resume" string="Resume"
|
|
type="object" class="btn-primary" icon="fa-play"
|
|
invisible="state != 'paused'"
|
|
help="Resume paused batch processing."/>
|
|
<button name="action_cancel" string="Cancel"
|
|
type="object" class="btn-secondary"
|
|
invisible="state not in ('queued', 'processing', 'paused')"
|
|
help="Stop the batch processing. Items already completed will be kept."/>
|
|
<button name="action_retry_failed" string="Retry Failed"
|
|
type="object" class="btn-warning"
|
|
invisible="failed_items == 0 or state not in ('done', 'failed')"
|
|
help="Retry generating content for all failed items"/>
|
|
<field name="state" widget="statusbar"
|
|
statusbar_visible="draft,queued,processing,done"
|
|
statusbar_colors='{"paused": "warning"}'/>
|
|
</header>
|
|
<sheet>
|
|
<div class="oe_button_box" name="button_box">
|
|
<button name="action_view_content" type="object"
|
|
class="oe_stat_button" icon="fa-file-text-o"
|
|
invisible="content_count == 0">
|
|
<field name="content_count" widget="statinfo" string="Content"/>
|
|
</button>
|
|
</div>
|
|
|
|
<div class="oe_title">
|
|
<h1>
|
|
<field name="name" placeholder="Batch Name"/>
|
|
</h1>
|
|
</div>
|
|
|
|
<!-- Paused Alert -->
|
|
<div class="alert alert-warning" role="alert"
|
|
invisible="state != 'paused'">
|
|
<strong><i class="fa fa-pause-circle"/> Paused:</strong>
|
|
Batch processing is paused. Click "Resume" to continue.
|
|
</div>
|
|
|
|
<!-- Progress Bar with ETA -->
|
|
<div class="alert alert-info" role="alert"
|
|
invisible="state not in ('queued', 'processing')">
|
|
<strong>Processing:</strong>
|
|
<field name="completed_items" class="oe_inline"/> /
|
|
<field name="total_items" class="oe_inline"/> items completed
|
|
<span invisible="eta_minutes == 0" class="ms-2">
|
|
— ETA: <field name="eta_minutes" class="oe_inline"/> min
|
|
</span>
|
|
<field name="progress_percent" widget="progressbar" class="mt-2"/>
|
|
</div>
|
|
|
|
<!-- Error Summary -->
|
|
<div class="alert alert-warning" role="alert" invisible="failed_items == 0">
|
|
<strong>Warning:</strong>
|
|
<field name="failed_items" class="oe_inline"/> items failed.
|
|
Check the items below for error details.
|
|
</div>
|
|
|
|
<group>
|
|
<group string="Source">
|
|
<field name="concurrency" readonly="state != 'draft'"
|
|
help="Items to process per cron run (1-10)"/>
|
|
<field name="source_type" widget="radio"
|
|
readonly="state != 'draft'"/>
|
|
<field name="product_ids" widget="many2many_tags"
|
|
invisible="source_type != 'products'"
|
|
readonly="state != 'draft'"/>
|
|
<field name="csv_file" filename="csv_filename"
|
|
invisible="source_type != 'csv'"
|
|
readonly="state != 'draft'"/>
|
|
<field name="csv_filename" invisible="1"/>
|
|
<field name="keywords_list"
|
|
invisible="source_type != 'keywords'"
|
|
readonly="state != 'draft'"
|
|
placeholder="keyword1, topic1 keyword2, topic2 ..."/>
|
|
</group>
|
|
<group string="Content Settings">
|
|
<field name="content_type" readonly="state != 'draft'"/>
|
|
<field name="template_id" readonly="state != 'draft'"
|
|
domain="[('content_type', '=', content_type)]"/>
|
|
<field name="brand_voice_id" readonly="state != 'draft'"/>
|
|
<field name="tone" readonly="state != 'draft'"/>
|
|
<field name="target_word_count" readonly="state != 'draft'"/>
|
|
<field name="language_id" readonly="state != 'draft'"/>
|
|
</group>
|
|
</group>
|
|
|
|
<group>
|
|
<group string="Image Settings">
|
|
<field name="include_images" widget="boolean_toggle"
|
|
readonly="state != 'draft'"/>
|
|
<field name="image_count" invisible="not include_images"
|
|
readonly="state != 'draft'"/>
|
|
<field name="image_style" invisible="not include_images"
|
|
readonly="state != 'draft'"/>
|
|
</group>
|
|
<group string="Blog Settings" invisible="content_type != 'blog_post'">
|
|
<field name="blog_id" readonly="state != 'draft'"
|
|
placeholder="Select target blog"/>
|
|
</group>
|
|
</group>
|
|
|
|
<group invisible="state == 'draft'">
|
|
<group string="Timing">
|
|
<field name="started_at"/>
|
|
<field name="completed_at"/>
|
|
<field name="duration" widget="float_time"/>
|
|
</group>
|
|
<group/>
|
|
</group>
|
|
|
|
<notebook invisible="not item_ids">
|
|
<page string="Items" name="items">
|
|
<field name="item_ids" readonly="state != 'draft'">
|
|
<list decoration-success="state == 'done'"
|
|
decoration-danger="state == 'failed'"
|
|
decoration-warning="state == 'processing'"
|
|
decoration-muted="state == 'cancelled'"
|
|
editable="bottom">
|
|
<field name="sequence" widget="handle"/>
|
|
<field name="name"/>
|
|
<field name="keywords"/>
|
|
<field name="topic" optional="hide"/>
|
|
<field name="product_id" optional="show"/>
|
|
<field name="state" widget="badge"
|
|
decoration-info="state in ('draft', 'pending')"
|
|
decoration-warning="state == 'processing'"
|
|
decoration-success="state == 'done'"
|
|
decoration-danger="state == 'failed'"
|
|
readonly="1"/>
|
|
<field name="content_id" optional="show" readonly="1"/>
|
|
<field name="error_message" optional="hide" readonly="1"/>
|
|
</list>
|
|
</field>
|
|
</page>
|
|
</notebook>
|
|
</sheet>
|
|
<chatter/>
|
|
</form>
|
|
</field>
|
|
</record>
|
|
|
|
<!-- Batch Search View -->
|
|
<record id="otk_seo_content_batch_view_search" model="ir.ui.view">
|
|
<field name="name">otk.seo.content.batch.search</field>
|
|
<field name="model">otk.seo.content.batch</field>
|
|
<field name="arch" type="xml">
|
|
<search string="Search Batches">
|
|
<field name="name"/>
|
|
<separator/>
|
|
<filter name="filter_draft" string="Draft"
|
|
domain="[('state', '=', 'draft')]"/>
|
|
<filter name="filter_processing" string="Processing"
|
|
domain="[('state', 'in', ('queued', 'processing'))]"/>
|
|
<filter name="filter_done" string="Completed"
|
|
domain="[('state', '=', 'done')]"/>
|
|
<filter name="filter_failed" string="Failed"
|
|
domain="[('state', '=', 'failed')]"/>
|
|
<separator/>
|
|
<filter name="filter_my_batches" string="My Batches"
|
|
domain="[('create_uid', '=', uid)]"/>
|
|
<group>
|
|
<filter name="group_state" string="Status"
|
|
context="{'group_by': 'state'}"/>
|
|
<filter name="group_source" string="Source Type"
|
|
context="{'group_by': 'source_type'}"/>
|
|
<filter name="group_date" string="Created Date"
|
|
context="{'group_by': 'create_date:month'}"/>
|
|
</group>
|
|
</search>
|
|
</field>
|
|
</record>
|
|
|
|
<!-- Batch Action -->
|
|
<record id="action_otk_seo_content_batch" model="ir.actions.act_window">
|
|
<field name="name">Bulk Generation</field>
|
|
<field name="res_model">otk.seo.content.batch</field>
|
|
<field name="view_mode">list,form</field>
|
|
<field name="search_view_id" ref="otk_seo_content_batch_view_search"/>
|
|
<field name="context">{'search_default_filter_my_batches': 1}</field>
|
|
<field name="help" type="html">
|
|
<p class="o_view_nocontent_smiling_face">
|
|
Create your first bulk generation job!
|
|
</p>
|
|
<p>
|
|
Generate SEO content for multiple products or topics at once.
|
|
Select products, upload a CSV, or enter keywords to get started.
|
|
</p>
|
|
</field>
|
|
</record>
|
|
|
|
</odoo>
|