Conversation
|
First of all: thanks for (re-)working (on) this. I'll try to comment on the other things inline. |
|
|
||
| SELECT | ||
| state >= p.dependent_ticket_trigger_state INTO satisfaction | ||
| dependent_ticket_state.sort >= configured_trigger_state.sort INTO satisfaction |
There was a problem hiding this comment.
I think with some careful migration patches it would be possible to get the ticket states into a useful native order.
But not sure if it'd be worth the effort.
There was a problem hiding this comment.
Not sure if this breaks the possibility of later changes without deleting all tickets, e.g. not being able to REPLACE the enum when there are references to it.
It is quite some code to use the sort property, but may be better in the long run.
There was a problem hiding this comment.
Inplace replacing is difficult, that's true. But one could introduce the new enum with a temporary name, add temporary columns to all related tables, copy the value from the old column, remove the old one and rename the enum column back to the old name. Should™ work ;)
There was a problem hiding this comment.
Sounds good.. but please create an issue for that. I like the idea, but dont want to do it in this PR...
| JOIN | ||
| tbl_ticket_state configured_trigger_state ON | ||
| t.ticket_type = 'encoding' AND | ||
| configured_trigger_state.ticket_state = p.dependent_ticket_trigger_state |
There was a problem hiding this comment.
It always takes a while for me to understand that code.
I think what confuses me, is the use of dependent and depending "tickets". One could read "dependent_ticket_state" as "the state of the ticket the given ticket is depending on" or as "the state of the given ticket which is depending on another ticket" (making it a dependent ticket).
I would propose to use "dependee" (https://en.wiktionary.org/wiki/dependee) and "depender" (https://en.wiktionary.org/wiki/depender), or just use "master ticket", whenever you mean the master ticket.
If you absolutely detest that, maybe I'm ok with more comments explaining the relationships.
There was a problem hiding this comment.
Oh and you should probably mention in the commit message, that you switched from using the param_ticket_id as the depender-ticket-id to the master (or dependee) ticket-id.
Which is confusing, since ticket_depending_encoding_ticket_state still asks for the depender-ticket-id.
Or did I miss anything?
There was a problem hiding this comment.
or just use "master ticket", whenever you mean the master ticket.
I'm probably the reason we're not currently doing this. As we set depends_on for encoding profiles, we have no notion of a master or an informal subticket anywhere else in the UI or code. Therefor i suggested something like dependent. I like dependee and maybe dependent? The last is a little more common. This would also free us from the language issues around master/slave.
There was a problem hiding this comment.
Dependee and dependent is fine with me.
Regarding the "master" notion, in #171 it's about to be called that, if I saw that correctly.
There was a problem hiding this comment.
in #171 it's about to be called that, if I saw that correctly.
I think this is only a comment and a UI label – I already requested changing this some time ago.
There was a problem hiding this comment.
The semantical change of the parameter is likely an error, I will investigate that.
| LEFT JOIN | ||
| tbl_ticket_state masterstate ON | ||
| masterstate.ticket_type = 'encoding' AND | ||
| masterstate.ticket_state = COALESCE(ticket_depending_encoding_ticket_state(t.id),pj.dependent_ticket_trigger_state) |
There was a problem hiding this comment.
Now that I see the use of "master" here, I'd be in favor to use it above as well. See comment above.
There was a problem hiding this comment.
In the last commit in this PR, the view is reworked again and the selection of the master ticket is much clearer. So I guess the same should be done in ticket_depending_encoding_ticket_state_satisfied, if the change of parameter semantics is reverted.
| WHERE | ||
| pj.read_only = false AND | ||
| t.ticket_type != 'meta' AND | ||
| t.ticket_type IN ('recording','encoding','ingest') AND |
There was a problem hiding this comment.
I'm just curious: why is that faster?
There was a problem hiding this comment.
Because for some reasons Postgres doesnt get it that this is actually the same. The newer line will result in using the ANY operation which will in turn make use of a hash index, while using != will result in a "simple filter" on a full index scan or even table scan.
| 'virtual_property_filter' => [$propertyFilters] | ||
| ]) | ||
| ->orderBy('ticket_priority(id) DESC'); | ||
| ->orderBy('calculated_priority DESC'); |
There was a problem hiding this comment.
Is there a particular reason why we order here again, when the view already returns ordered results?
There was a problem hiding this comment.
This is probably just legacy and/or a case of "better safe than sorry".
| CREATE INDEX tbl_ticket_handle_id_idx ON tbl_ticket USING btree(handle_id); | ||
| CREATE INDEX tbl_ticket_parent_id_idx ON tbl_ticket USING hash(parent_id); | ||
| CREATE INDEX tbl_ticket_project_id_idx ON tbl_ticket USING hash(project_id); | ||
| CREATE INDEX tbl_ticket_view_servicable_idx ON tbl_ticket USING btree(failed, service_executable, ticket_type); |
There was a problem hiding this comment.
Those indexes are missing in the migration file.
There was a problem hiding this comment.
Mh I guess the whole migration patch file is not updated.
Edit: Oh you mentioned that in the PR comment. Sorry!
There was a problem hiding this comment.
Oh, and tbl_ticket_project_id_idx already exists. See line 136.
There was a problem hiding this comment.
Good catch with the duplicate index, will change the name.
|
@pegro The "squashing in" did not mean I want to squash the commits/ the PR once it is approved. It's the solely purpose of this PR to introduce multiple commits with more explanation. |
|
Yes, makes sense. ;) |
… comparison Belongs to feature #157. Enums do not have correct native order, instead a dedicated sort property exists, so this must be used to check if the configured state is reached by the dependent ticket.
Using a function for ordering seems to be not optimized by Postgres and therefore very expensive. Additionally, it seems with older Postgres versions this makes the use of LIMIT impossible when querying the view.
Eliminate another function call in a JOIN clause by incorporating the logic. Limit performance impact by using LATERAL JOIN.
| @@ -137,7 +137,6 @@ CREATE INDEX tbl_ticket_project_id_idx ON tbl_ticket USING btree(project_id); | |||
| CREATE INDEX tbl_ticket_fahrplan_id_idx ON tbl_ticket USING btree(fahrplan_id); | |||
| CREATE INDEX tbl_ticket_handle_id_idx ON tbl_ticket USING btree(handle_id); | |||
| CREATE INDEX tbl_ticket_parent_id_idx ON tbl_ticket USING hash(parent_id); | |||
There was a problem hiding this comment.
The existing indexes were btree indexes, the added ones are hash indexes. According to the PostgreSQL documentation they are of limited use: Hash indexes can only handle simple equality comparisons [...]. Maybe change them to btree indexes?!
There was a problem hiding this comment.
This is intentional. You usually do not query "less than" or "greater than" for things like IDs. Unfortunately in my tests those indexes were not used according to the execution plan when they were of type btree. Makes some sense in my head for JOINS. I can test that again if you think btree should be used by the query optimizer in every case a hash index is used.
There was a problem hiding this comment.
Ok, so this was a conscious choice. Just wanted to make sure.
| wantedstate.ticket_type = t2.ticket_type AND | ||
| wantedstate.ticket_state = p.dependent_ticket_trigger_state | ||
| tbl_ticket_state configured_trigger_state ON | ||
| depender_ticket.ticket_type = 'encoding' AND |
There was a problem hiding this comment.
I get that the JOIN conditions in line 24 and 28 filter for encoding tickets, but since they don't refer to the table joined, there might be multiple ticket states with the same ticket_state value?!
There was a problem hiding this comment.
But ticket_state is an enum and therefore unique, isnt it? The JOIN is meant to deliver the state attributes for encoding tickets and NULLs for other ticket types. So is your concern that these JOINS produce more tupels? I cannot think of a case where this might happen.
If your concern is that dependee_ticket_state and configured_trigger_state might contain the same tupel of the state table, then yes this is possible of course.
There was a problem hiding this comment.
ticket_state is an enum, but tbl_ticket_state is a table (which you are joining here) and it contains multiple rows with e.g. ticket_state = 'removing'. I know, it's not really likely that the trigger state would be one of those, but technically it could happen.
The JOIN is meant to deliver the state attributes for encoding tickets
But the ticket_type of tbl_ticket_state is not part of any condition... That's what I'm referring to.
There was a problem hiding this comment.
Now I know what you mean. I had in memory that the states are unique, but they aren't. So this clash could happen for example with the state "gone". You are absolutely right, there needs to be an additional or changed condition. For easy review, I will put a commit for this on top of the branch (and another one for truncating old migration file).
There was a problem hiding this comment.
Looks good, although I'd have used dependee_ticket_state.ticket_type = depender_ticket.ticket_type just to have the hard-coded value only once.
There was a problem hiding this comment.
And since you don't do any left joins and such, I'd suggest to move the depender_ticket.ticket_type = 'encoding' condition to the where clause, to only have it once. The function should still return NULL, if the ticket is not a encoding ticket.
| @@ -3,17 +3,17 @@ BEGIN; | |||
| SET ROLE TO postgres; | |||
There was a problem hiding this comment.
I guess this migration file could just be removed.
There was a problem hiding this comment.
No thats a bigger change, because it contains ADD COLUMN dependent_ticket_trigger_state, while the newer migration file contains a RENAME of that column.
I wanted to leave it in there in this PR because some installations are in that state currently. But it could be shrunk to the ADD COLUMN part.
There was a problem hiding this comment.
Yes, I'd be in favor of shrinking.
* refactor names to clarify dependency relationship * add indexes for performance * copy logic of functions into view_servicable_tickets to improve query times
|
@pegro please have a look at the last 3 commits from the latest batch. Another round of testing is still outstanding. |
| wantedstate.ticket_type = t2.ticket_type AND | ||
| wantedstate.ticket_state = p.dependent_ticket_trigger_state | ||
| tbl_ticket_state configured_trigger_state ON | ||
| depender_ticket.ticket_type = 'encoding' AND |
There was a problem hiding this comment.
Looks good, although I'd have used dependee_ticket_state.ticket_type = depender_ticket.ticket_type just to have the hard-coded value only once.
| wantedstate.ticket_type = t2.ticket_type AND | ||
| wantedstate.ticket_state = p.dependent_ticket_trigger_state | ||
| tbl_ticket_state configured_trigger_state ON | ||
| depender_ticket.ticket_type = 'encoding' AND |
There was a problem hiding this comment.
And since you don't do any left joins and such, I'd suggest to move the depender_ticket.ticket_type = 'encoding' condition to the where clause, to only have it once. The function should still return NULL, if the ticket is not a encoding ticket.
| LEFT JOIN | ||
| tbl_ticket_state wantedstate ON wantedstate.ticket_type = 'encoding' AND wantedstate.ticket_state = pj.dependent_ticket_trigger_state | ||
| tbl_ticket_state configured_trigger_state ON | ||
| configured_trigger_state.ticket_type = 'encoding' AND |
There was a problem hiding this comment.
I guess configured_trigger_state.ticket_type = t.ticket_type would do the same, but it always be encoding as long we don't allow other ticket types as encoding to have a encoding_profile_version_id set.
I'm ok with this. It's just I like to avoid as much hard-coding as possible without performance impact.
|
Fine with me |
See issue #166 .
Functionality testing still outstanding. Some minor, mostly cosmetic differences to current maser exist.
Feel free to add commits to this branch, I'll squash them in before removing WIP status. Accordingly, expect history rewrites in this branch as long as it is in WIP status.
The current last migration file will be replaced in a final commit when removing WIP state. If there are other migrations in the meantime, then a suitable change will be added.