Skip to content

[16.0][ADD] project_task_create_portal: Module added#1578

Open
geomer198 wants to merge 6 commits into
OCA:16.0from
xxp-odoo-erp:16.0-t0088-project_task_create_portal-add
Open

[16.0][ADD] project_task_create_portal: Module added#1578
geomer198 wants to merge 6 commits into
OCA:16.0from
xxp-odoo-erp:16.0-t0088-project_task_create_portal-add

Conversation

@geomer198

Copy link
Copy Markdown

No description provided.

@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch from 1db972f to 34dac90 Compare October 7, 2025 22:31
@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch from 34dac90 to f2e45e1 Compare October 7, 2025 22:38
@geomer198 geomer198 closed this Oct 8, 2025
@geomer198 geomer198 reopened this Oct 8, 2025
@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch from 5f4ccc9 to a47028f Compare October 16, 2025 21:20

@gfcapalbo gfcapalbo left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Create and edit work well. tests look solid, but there are some problems.

  • incompatible with project_task_code_portal, that loads the task page with sudo user, therefore making the edit button dissapear from form (env.user != task.create_uid)
  • the edit button is visible when accessing portal task form from projects > task , but not directly from tasks > task. this is caused by the widespread sudo problem in portal templates. solved by:
          def is_portal_task_creation_allowed(self):
                 self.ensure_one()
                 return bool(self.portal_stage_id) and self.env.context['uid'] in self.portal_user_ids.ids

created an MR to this branch with the proposed fixes for this problem.

  • settings name only refers to "create" , make clear also "edit" is possible.
  • in settings make clear that stage_id is bothe the stage the new task will be created in and also the only stage it will be allowed to be edited in.
  • Optionally, refactor to have, also separate "edit" setting on project form.
  • Module name is misleading, it allows to edit and create tasks.


- Go to the portal, navigate to Projects
- Select an available project
- Select a task in the stage permitted for task creation and task editing

@gfcapalbo gfcapalbo Nov 14, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Edit button not visible on task form. should be under

    task, history , does not show. (explanation of reason in other comments)

priority="20"
>
<xpath expr="//t[@t-set='entries']/ul" position="inside">
<li class="list-group-item" t-if="task.check_portal_edit_access()">

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

here we have our edit button, that will refer to the edit controller, only for records in correct stage and owned by users.

Edit works perfectly, but it is incompatible with module project_task_code_portal, if that module is installed all edit functions are gone. route is still accessible by manually inserting the url.

The reason for this incompatibility lies in this line of code: https://github.com/OCA/project/blob/16.0/project_task_code_portal/controllers/portal.py#L87
where we freturn sudo page values:
https://github.com/OCA/project/blob/16.0/project_task_code_portal/controllers/portal.py#L91

then leaving self.env.user as sudo in the task page. In other comments i suggest to replace self.env.user with self.env.context['uid'], to make code work with project_task_code_portal and any other modules that may sudo the page.

"""Check if the current user has portal access to edit this task."""
# Portal users can only access tasks in projects with portal task creation enabled
if not self.project_id.is_portal_task_creation_allowed():
return False

@gfcapalbo gfcapalbo Nov 14, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why would edit be forbidden , because creation is not allowed?

Yes, our edit feature is tied to "only the tasks the user has created" but this would cause problems if we have a situation a user creates many tasks, is then removed from create permissions , but still wants to modify the issues they created.

I suggest to remove this. edit should be depending only on the current user and record creator .

Or create separate configuration settings for edit function.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to add to add it here, In the write where check_portal_edit_access is called you might want to add self.ensure_one() because write call can be called with multi-records. Either add self.ensure_one() or for loop that will loop over self just in case its called with multi recordset.

<field name="arch" type="xml">
<group name="extra_settings" position="before">
<group
string="Allow Create Task In Portal"

@gfcapalbo gfcapalbo Nov 14, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Create and edit own tasks in portal.
settings name is misleading.

Comment thread project_task_create_portal/README.rst Outdated
@@ -0,0 +1,124 @@
============================
Project Portal Task Creation

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Misleading name. this module supports create and has also an "own task edit" feature

def is_portal_task_creation_allowed(self):
"""Check if portal task creation is allowed for this project."""
self.ensure_one()
return bool(self.portal_stage_id) and self.env.user in self.portal_user_ids

@gfcapalbo gfcapalbo Nov 14, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

because of a sudo in project_task_code_portal, this will fail everytime, therefore all edit features will not show (the button is conditionally checked on this being true)

Works if replaced by:
return bool(self.portal_stage_id) and self.env.context['uid'] in self.portal_user_ids.ids

this problem was found on runboat with all oca/project modules installed.

return False

# Portal users can only edit their own tasks
if self.create_uid != self.env.user:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if self.env.user is sudo, as imposed in project_task_code_portal this will fail.
replace self.env.user with self.env.context['uid']

gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 14, 2025
if not self.env.user.has_group("base.group_portal"):
return records
for record in self:
if not record.project_id.is_portal_task_creation_allowed():

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think here you meant to loop through the record set returned by records = super().create(vals_list) otherwise I don't think the call to is_portal_task_creation_allowed() is being executed.

"""Check if the current user has portal access to edit this task."""
# Portal users can only access tasks in projects with portal task creation enabled
if not self.project_id.is_portal_task_creation_allowed():
return False

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just to add to add it here, In the write where check_portal_edit_access is called you might want to add self.ensure_one() because write call can be called with multi-records. Either add self.ensure_one() or for loop that will loop over self just in case its called with multi recordset.

"""Override write to handle portal user restrictions."""
if (
self.env.user.has_group("base.group_portal")
and not self.check_portal_edit_access()

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is what I meant when write is called and check_portal_edit_access isn't secured to check multiple records or single check.

gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 19, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 25, 2025
@geomer198

Copy link
Copy Markdown
Author

@gfcapalbo, @KKamaa
Thanks for the code review! I've updated the code based on your feedback. Could you please review again to confirm everything is correct?

- Module name is updated on "Project Portal Own Task Management"
- ensure_one method is added for method "is_portal_task_creation_allowed"
- Сompatibility with project_task_code_portal is added
- Project settings group description is updated
@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch from 8c48953 to 5a8a62c Compare November 25, 2025 16:55
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 25, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 25, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Nov 26, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Dec 1, 2025
gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Dec 5, 2025

@alexey-pelykh alexey-pelykh left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for this contribution. The concept of portal task create/edit is genuinely useful and the test coverage is solid. However, there are several issues that need to be addressed before this can be merged.

Security -- missing ir.model.access.csv and record rules. This module adds new fields and behaviors for portal users but does not ship any security/ir.model.access.csv file. The controller uses sudo() to bypass access checks, but the model-level write() override relies on application-level logic rather than proper Odoo record rules. You should define proper ir.rule record rules restricting portal users' access.

Security -- no field-level write restriction in write(). The write() override checks check_portal_edit_access() but does not restrict which fields a portal user may modify. A crafted POST request could include stage_id, project_id, user_ids, or any other field, and the sudo().write() in the controller would apply them.

Security -- create() iterates self instead of records. In project_task.py, for record in self iterates the model class rather than the newly created records. The permission check after creation is never actually executed.

Manifest -- syntax issue in summary. The summary value spans two lines as two implicit string literals -- please verify the concatenation works as intended.

Other issues:

  • console.log(this._wysiwyg) left in portal.js -- debug statement, must be removed.
  • Dead code in portal.js: _onEditProfilePicClick, _onFileUploadChange, _onProfilePicClearClick are never bound to events. Remove them.
  • Sorting entry key create_date with label "Created by" and order create_uid desc is inconsistent.
  • README files use Markdown syntax inside .rst files.
  • Typo in CONFIGURE.rst: "Se the" should be "Set the".

Happy to re-review once updated.


def check_portal_edit_access(self):
"""Check if the current user has portal access to edit this task."""
# Portal users can only access tasks in projects with portal task creation enabled

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Bug: for record in self iterates the model (empty recordset in create context), not the newly created records. Should be for record in records. As written, the permission check after super().create() is never executed for portal users.

# Portal users can only access tasks in the allowed stage
if self.stage_id != self.project_id.portal_stage_id:
return False

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Security: the write() override does not restrict which fields a portal user can write. A crafted request bypassing the controller could modify stage_id, project_id, priority, etc. Consider filtering vals against allowed fields when the user is a portal user.

.removeClass("float-start");
this._wysiwyg = wysiwyg;
this._wysiwyg.$editable.addClass("bg-white p-2");
console.log(this._wysiwyg);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Debug statement: console.log(this._wysiwyg) must be removed before merge.

* @private
* @param {Event} ev
*/
_onEditProfilePicClick: function (ev) {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Dead code: _onEditProfilePicClick, _onFileUploadChange, and _onProfilePicClearClick are not bound to any events in this widget. These appear copy-pasted from website_forum. Please remove.

- Go to the "Settings" tab

- Set the **Portal Task Creation Stage** to a stage (from the project’s stages) from which portal users will be allowed to add tasks.
- Se the **Hide assigned user** to hide the assigned user of the task on the portal.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Typo: "Se the" should be "Set the".

gfcapalbo added a commit to gfcapalbo/project that referenced this pull request Mar 17, 2026
@github-actions

github-actions Bot commented Jul 5, 2026

Copy link
Copy Markdown

There hasn't been any activity on this pull request in the past 4 months, so it has been marked as stale and it will be closed automatically if no further activity occurs in the next 30 days.
If you want this PR to never become stale, please ask a PSC member to apply the "no stale" label.

@github-actions github-actions Bot added the stale PR/Issue without recent activity, it'll be soon closed automatically. label Jul 5, 2026
@OCA-git-bot OCA-git-bot added series:16.0 mod:project_task_create_portal Module project_task_create_portal labels Jul 17, 2026
@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch 2 times, most recently from 20e226d to d1bc272 Compare July 17, 2026 20:44
@geomer198
geomer198 force-pushed the 16.0-t0088-project_task_create_portal-add branch from d1bc272 to 15bfa6d Compare July 17, 2026 20:55
@geomer198

Copy link
Copy Markdown
Author

@alexey-pelykh Could you please check changes?

@github-actions github-actions Bot removed the stale PR/Issue without recent activity, it'll be soon closed automatically. label Jul 19, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

mod:project_task_create_portal Module project_task_create_portal series:16.0

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants