Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
- Package list UI now updates immediately after blacklist changes
- Channel edit dialog filters out blacklisted packages from selection
- Floor package selection prevents choosing blacklisted packages with clear visual feedback
- **Group rollout state moved to runtime-local table:** The `rollout_in_progress` flag on `groups` is now stored in a separate `group_state` table, in preparation for the distributed Nebraska topology described in [RFC #1375](https://github.com/flatcar/nebraska/issues/1375). The JSON contract is unchanged. ([#1396](https://github.com/flatcar/nebraska/pull/1396))

### Removed
### Bugfixes
Expand Down
2 changes: 2 additions & 0 deletions backend/pkg/api/db/drop_all_tables.sql
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ drop table if exists package cascade;
drop table if exists flatcar_action cascade;
drop table if exists channel cascade;
drop table if exists groups cascade;
drop table if exists group_state cascade;
drop table if exists instance cascade;
drop table if exists instance_status cascade;
drop table if exists instance_application cascade;
Expand All @@ -14,5 +15,6 @@ drop table if exists event cascade;
drop table if exists activity cascade;
drop table if exists package_channel_blacklist cascade;
drop table if exists database_migrations;
drop function if exists create_group_state_for_group();
-- Legacy tables if we're dropping tables in a non-migrated DB
drop table if exists coreos_action cascade;
40 changes: 40 additions & 0 deletions backend/pkg/api/db/migrations/0022_add_group_state_table.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
-- +migrate Up

create table group_state (
group_id uuid primary key references groups (id) on delete cascade,
rollout_in_progress boolean default false not null,
created_ts timestamptz default current_timestamp not null
);

insert into group_state (group_id, rollout_in_progress, created_ts)
select id, rollout_in_progress, created_ts from groups;

-- +migrate StatementBegin
create or replace function create_group_state_for_group() returns trigger as $$
begin
insert into public.group_state (group_id) values (new.id)
on conflict (group_id) do nothing;
return new;
end;
$$ language plpgsql;
-- +migrate StatementEnd

create trigger groups_create_group_state
after insert on groups
for each row
execute function create_group_state_for_group();

alter table groups enable always trigger groups_create_group_state;

alter table groups drop column rollout_in_progress;

-- +migrate Down

alter table groups add column rollout_in_progress boolean default false not null;

update groups set rollout_in_progress = gs.rollout_in_progress
from group_state gs where groups.id = gs.group_id;

drop trigger if exists groups_create_group_state on groups;
drop function if exists create_group_state_for_group();
drop table if exists group_state;
17 changes: 9 additions & 8 deletions backend/pkg/api/db/sample_data.sql
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,10 @@ insert into package values ('284d295b-518f-4d67-999e-94968d0eed90', 1, '829.0.0'
insert into channel values ('e06064ad-4414-4904-9a6e-fd465593d1b2', 'stable', '#14b9d6', '2019-08-19 05:09:34.261241', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', '337b3f7e-ff29-47e8-a052-f0834d25bdb5', 1);
insert into channel values ('128b8c29-5058-4643-8e67-a1a0e3c641c9', 'beta', '#fc7f33', '2019-08-19 05:09:34.264334', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', '337b3f7e-ff29-47e8-a052-f0834d25bdb5', 1);
insert into channel values ('a87a03ad-4984-47a1-8dc4-3507bae91ee1', 'alpha', '#1fbb86', '2019-08-19 05:09:34.265754', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', '284d295b-518f-4d67-999e-94968d0eed90', 1);
insert into groups values ('9a2deb70-37be-4026-853f-bfdd6b347bbe', 'Stable', 'For production clusters', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', 'e06064ad-4414-4904-9a6e-fd465593d1b2', 'stable');
insert into groups values ('3fe10490-dd73-4b49-b72a-28ac19acfcdc', 'Beta', 'Promoted alpha releases, to catch bugs specific to your configuration', true, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.273244', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', '128b8c29-5058-4643-8e67-a1a0e3c641c9', 'beta');
insert into groups values ('5b810680-e36a-4879-b98a-4f989e80b899', 'Alpha', 'Tracks current development work and is released frequently', false, true, true, false, 'Europe/Berlin', '15 minutes', 1, '30 minutes', '2019-08-19 05:09:34.274911', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', 'a87a03ad-4984-47a1-8dc4-3507bae91ee1', 'alpha');
insert into groups values ('9a2deb70-37be-4026-853f-bfdd6b347bbe', 'Stable', 'For production clusters', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', 'e06064ad-4414-4904-9a6e-fd465593d1b2', 'stable');
insert into groups values ('3fe10490-dd73-4b49-b72a-28ac19acfcdc', 'Beta', 'Promoted alpha releases, to catch bugs specific to your configuration', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.273244', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', '128b8c29-5058-4643-8e67-a1a0e3c641c9', 'beta');
update group_state set rollout_in_progress = true where group_id = '3fe10490-dd73-4b49-b72a-28ac19acfcdc';
insert into groups values ('5b810680-e36a-4879-b98a-4f989e80b899', 'Alpha', 'Tracks current development work and is released frequently', true, true, false, 'Europe/Berlin', '15 minutes', 1, '30 minutes', '2019-08-19 05:09:34.274911', 'e96281a6-d1af-4bde-9a0a-97b76e56dc57', 'a87a03ad-4984-47a1-8dc4-3507bae91ee1', 'alpha');
insert into flatcar_action values ('b2b16e2e-57f8-4775-827f-8f0b11ae9bd2', 'postinstall', '', 'k8CB8tMe0M8DyZ5RZwzDLyTdkHjO/YgfKVn2RgUMokc=', false, false, true, '', '', '', '2019-08-20 00:12:37.532281', '2ba4c984-5e9b-411e-b7c3-b3eb14f7a261');
insert into flatcar_action values ('d5a2cbf3-b810-4e8c-88e8-6df91fc264c6', 'postinstall', '', 'QUGnmP51hp7zy+++o5fBIwElInTAms7/njnkxutn/QI=', false, false, true, '', '', '', '2019-08-20 06:15:29.11685', '337b3f7e-ff29-47e8-a052-f0834d25bdb5');
insert into flatcar_action values ('299c54d1-3344-4ae9-8ad2-5c63d56d6c14', 'postinstall', '', 'SCv89GYzx7Ix+TljqbNsd7on65ooWqBzcCrLFL4wChQ=', false, false, true, '', '', '', '2019-08-20 00:09:06.927461', 'c2a36312-b989-403e-ab57-06c055a7eac2');
Expand All @@ -43,10 +44,10 @@ insert into package (id, type, url, filename, version, application_id, arch) val
insert into channel (id, name, color, application_id, package_id, arch) values ('bfe32b4a-5f8c-11e5-9d70-feff819cdc9f', 'Master', '#00CC00', 'b6458005-8f40-4627-b33b-be70a718c48e', '8004bad8-5f97-11e5-9d70-feff819cdc9f', 1);
insert into channel (id, name, color, application_id, package_id, arch) values ('cb2deea8-5f83-11e5-9d70-feff819cdc9f', 'Stable', '#0099FF', 'b6458005-8f40-4627-b33b-be70a718c48e', '12697fa4-5f83-11e5-9d70-feff819cdc9f', 1);
insert into channel (id, name, color, application_id, package_id, arch) values ('dddddddd-5f83-11e5-9d70-feff819cdc9f', 'Failing', '#AA99FF', 'b6458005-8f40-4627-b33b-be70a718c48e', 'aaaaaaaa-5f98-11e5-9d70-feff819cdc9f', 1);
insert into groups values ('bcaa68bc-5f82-11e5-9d70-feff819cdc9f', 'Prod EC2 us-west-2', 'Production servers, west coast', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'cb2deea8-5f83-11e5-9d70-feff819cdc9f', 'bcaa68bc-5f82-11e5-9d70-feff819cdc9f');
insert into groups values ('7074264a-2070-4b84-96ed-8a269dba5021', 'Prod EC2 us-east-1', 'Production servers, east coast', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'cb2deea8-5f83-11e5-9d70-feff819cdc9f', '7074264a-2070-4b84-96ed-8a269dba5021');
insert into groups values ('b110813a-5f82-11e5-9d70-feff819cdc9f', 'Qa-Dev', 'QA and development servers, Sydney', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'bfe32b4a-5f8c-11e5-9d70-feff819cdc9f', 'b110813a-5f82-11e5-9d70-feff819cdc9f');
insert into groups values ('cccccccc-5f82-11e5-9d70-feff819cdc9f', 'Failing Qa-Dev', 'Failing QA and development servers, Sydney', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'dddddddd-5f83-11e5-9d70-feff819cdc9f', 'cccccccc-5f82-11e5-9d70-feff819cdc9f');
insert into groups values ('bcaa68bc-5f82-11e5-9d70-feff819cdc9f', 'Prod EC2 us-west-2', 'Production servers, west coast', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'cb2deea8-5f83-11e5-9d70-feff819cdc9f', 'bcaa68bc-5f82-11e5-9d70-feff819cdc9f');
insert into groups values ('7074264a-2070-4b84-96ed-8a269dba5021', 'Prod EC2 us-east-1', 'Production servers, east coast', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'cb2deea8-5f83-11e5-9d70-feff819cdc9f', '7074264a-2070-4b84-96ed-8a269dba5021');
insert into groups values ('b110813a-5f82-11e5-9d70-feff819cdc9f', 'Qa-Dev', 'QA and development servers, Sydney', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'bfe32b4a-5f8c-11e5-9d70-feff819cdc9f', 'b110813a-5f82-11e5-9d70-feff819cdc9f');
insert into groups values ('cccccccc-5f82-11e5-9d70-feff819cdc9f', 'Failing Qa-Dev', 'Failing QA and development servers, Sydney', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', 'b6458005-8f40-4627-b33b-be70a718c48e', 'dddddddd-5f83-11e5-9d70-feff819cdc9f', 'cccccccc-5f82-11e5-9d70-feff819cdc9f');
insert into instance (id, ip) values ('instance1', '10.0.0.1');
insert into instance (id, ip) values ('instance2', '10.0.0.2');
insert into instance (id, ip) values ('instance3', '10.0.0.3');
Expand Down Expand Up @@ -93,4 +94,4 @@ insert into application (id, name, description, team_id) values ('780d6940-9a48-
insert into package (id, type, url, filename, version, application_id, arch) values ('efb186c9-d5cb-4df2-9382-c4821e4dcc4b', 4, 'http://localhost:8000/', 'demo_v1.0.0', '1.0.0', '780d6940-9a48-4414-88df-95ba63bbe9cb', 1);
insert into package (id, type, url, filename, version, application_id, arch) values ('ba28af48-b5b9-460e-946a-eba906ce7daf', 4, 'http://localhost:8000/', 'demo_v1.0.1', '1.0.1', '780d6940-9a48-4414-88df-95ba63bbe9cb', 1);
insert into channel (id, name, color, application_id, package_id, arch) values ('a7c8c9a4-d2a3-475d-be64-911ff8d6e997', 'Master', '#14b9d6', '780d6940-9a48-4414-88df-95ba63bbe9cb', 'efb186c9-d5cb-4df2-9382-c4821e4dcc4b', 1);
insert into groups values ('51a32aa9-3552-49fc-a28c-6543bccf0069', 'Master - dev', 'The latest stuff will be always here', false, true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', '780d6940-9a48-4414-88df-95ba63bbe9cb', 'a7c8c9a4-d2a3-475d-be64-911ff8d6e997', '51a32aa9-3552-49fc-a28c-6543bccf0069');
insert into groups values ('51a32aa9-3552-49fc-a28c-6543bccf0069', 'Master - dev', 'The latest stuff will be always here', true, true, false, 'Europe/Berlin', '15 minutes', 2, '60 minutes', '2019-08-19 05:09:34.269062', '780d6940-9a48-4414-88df-95ba63bbe9cb', 'a7c8c9a4-d2a3-475d-be64-911ff8d6e997', '51a32aa9-3552-49fc-a28c-6543bccf0069');
28 changes: 19 additions & 9 deletions backend/pkg/api/groups.go
Original file line number Diff line number Diff line change
Expand Up @@ -198,7 +198,7 @@ func (api *API) AddGroup(group *Group) (*Group, error) {
return nil, err
}
api.updateCachedGroups()
return group, nil
return api.GetGroup(group.ID)
}

// UpdateGroup updates an existing group using the context of the group
Expand Down Expand Up @@ -284,7 +284,7 @@ func (api *API) DeleteGroup(groupID string) error {
func (api *API) GetGroup(groupID string) (*Group, error) {
var group Group

query, _, err := goqu.From("groups").
query, _, err := api.groupsQuery().
Where(goqu.C("id").Eq(groupID)).
ToSQL()
if err != nil {
Expand Down Expand Up @@ -504,11 +504,13 @@ func (api *API) disableUpdates(groupID string) error {
}

// setGroupRolloutInProgress updates the value of the rollout_in_progress flag
// for a given group, indicating if a rollout is taking place now or not.
// for a given group, indicating if a rollout is taking place now or not. The
// flag lives on the runtime-local group_state table. The row is guaranteed to
// exist by the AFTER INSERT trigger on groups.
func (api *API) setGroupRolloutInProgress(groupID string, inProgress bool) error {
query, _, err := goqu.Update("groups").
query, _, err := goqu.Update("group_state").
Set(goqu.Record{"rollout_in_progress": inProgress}).
Where(goqu.C("id").Eq(groupID)).
Where(goqu.C("group_id").Eq(groupID)).
ToSQL()
if err != nil {
return err
Expand All @@ -521,11 +523,19 @@ func (api *API) setGroupRolloutInProgress(groupID string, inProgress bool) error
// groupsQuery returns a SelectDataset prepared to return all groups. This
// query is meant to be extended later in the methods using it to filter by a
// specific group id, all groups of a given app, specify how to query the rows
// or their destination.
// or their destination. The join with group_state pulls in rollout_in_progress,
// which lives on the group_state table.
func (api *API) groupsQuery() *goqu.SelectDataset {
query := goqu.From("groups").Order(goqu.I("created_ts").Desc())

return query
return goqu.From("groups").
InnerJoin(
goqu.T("group_state"),
goqu.On(goqu.I("groups.id").Eq(goqu.I("group_state.group_id"))),
).
Select(
goqu.T("groups").All(),
goqu.I("group_state.rollout_in_progress"),
).
Order(goqu.I("groups.created_ts").Desc())
}

// GetGroupVersionBreakdown returns a version breakdown of all instances running on a given group.
Expand Down