From 2ea95934a4e6035f996d1b532dc16cf37be22ec8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Thu, 24 Feb 2022 12:32:06 +0000 Subject: [PATCH 01/66] fix limiting one allocation in utf8 tasks --- tools/testtool/commands/test_submission.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/testtool/commands/test_submission.go b/tools/testtool/commands/test_submission.go index 70f964db..9338b838 100644 --- a/tools/testtool/commands/test_submission.go +++ b/tools/testtool/commands/test_submission.go @@ -378,7 +378,7 @@ func runTests(testDir, privateRepo, problem string) error { } func noMoreThanTwoTimesWorse(old, new *benchstat.Metrics) (float64, error) { - if new.Mean > 2*old.Mean { + if new.Mean > 1.99*old.Mean { return 0.0, nil } From 8d5d80933d3a7d1141e0ee4a5a7e721ab357a647 Mon Sep 17 00:00:00 2001 From: Covariance Date: Sat, 19 Feb 2022 14:58:36 +0000 Subject: [PATCH 02/66] Update README.md --- varfmt/README.md | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/varfmt/README.md b/varfmt/README.md index 58a2b659..9de3ea0d 100644 --- a/varfmt/README.md +++ b/varfmt/README.md @@ -3,11 +3,10 @@ Реализуйте функцию `varfmt.Sprintf`. Функция принимает формат строку и переменное число аргументов. Синтаксис формат-строки похож на формат-строки питона: - - `{}` - задаёт ссылку на аргумент - - `{number}` - ссылается на аргумент с индексом `number` - - `{}` ссылается на аргумент с индексом равным позиции `{}` внутри паттерна +- `{number}` - ссылается на аргумент с индексом `number` +- `{}` - задаёт ссылку на аргумент с индексом, равным позиции `{}` среди всех ссылок (как `{}`, так и `{number}`) внутри паттерна -Например, `varfmt.Sprintf("{1} {0}", "Hello", "World")` должен вернуть строку `World Hello`. +Например, `varfmt.Sprintf("{1} {0}", "Hello", "World")` должен вернуть строку `World Hello`, а `varfmt.Sprintf("{0} {}", "Hello", "World")` должен вернуть строку `Hello World`. Аргументы функции могут быть произвольными типами. Вам нужно форматировать их так же, как это делает функция `fmt.Sprint`. Вызывать `fmt.Sprint` для форматирования отдельного аргумента From 90a66ba73f1e8488e760fa9a28d690898ce8c60c Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Feb 2022 22:26:41 +0300 Subject: [PATCH 03/66] Release Interfaces --- .deadlines.yml | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index 97773b86..7e950a36 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,18 @@ +- group: Interfaces + start: 24-02-2022 18:00 + deadline: 06-03-2022 23:59 + tasks: + - task: otp + score: 100 + - task: lrucache + score: 100 + - task: externalsort + score: 100 + - task: retryupdate + score: 100 + - task: ciletters + score: 100 + - group: Basics start: 17-02-2022 18:00 deadline: 27-02-2022 23:59 From 2995b5fa5ec554b20d1a02f77e026f80d787023d Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Feb 2022 22:35:05 +0300 Subject: [PATCH 04/66] [ciletters] Ask to use embed. --- ciletters/README.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/ciletters/README.md b/ciletters/README.md index 70bc4f03..4c8f7061 100644 --- a/ciletters/README.md +++ b/ciletters/README.md @@ -1,7 +1,8 @@ ## ciletters В этой задаче вам предстоит познакомиться со стандартным пакетом [text/template](https://golang.org/pkg/text/template/), -позволяющим генерировать текст в определенном формате. +позволяющим генерировать текст в определенном формате, а также с пакетом [embed](https://pkg.go.dev/embed), +позволяющим вкомпиливать в исполняемый файл строковые литералы. ### Легенда @@ -20,6 +21,8 @@ Нужно реализовать функцию `MakeLetter` из файла [letter.go](./letter.go), которая по go объекту нотификации генерирует её текстовое представление. +Для этого нужно написать `text/template` шаблон, сохранить его в отдлеьный файл, а затем получить его содержимое в коде с помомщью `go:embed`. + #### Прокомментированный пример из теста ``` Your pipeline #194613 has failed! // 194613 -- это ID pipeline'а From dcc644ed370247370a489029e484f6a12d8cf168 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Mon, 28 Feb 2022 17:38:27 +0000 Subject: [PATCH 05/66] Update .deadlines.yml --- .deadlines.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.deadlines.yml b/.deadlines.yml index 7e950a36..f774cc86 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,6 +1,6 @@ - group: Interfaces start: 24-02-2022 18:00 - deadline: 06-03-2022 23:59 + deadline: 13-03-2022 23:59 tasks: - task: otp score: 100 @@ -15,7 +15,7 @@ - group: Basics start: 17-02-2022 18:00 - deadline: 27-02-2022 23:59 + deadline: 06-03-2022 23:59 tasks: - task: hotelbusiness score: 100 From 0244492d9df67ee1c2ef07dc15ce58a0666c567f Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 3 Mar 2022 09:54:07 +0300 Subject: [PATCH 06/66] Release goroutines task group. --- .deadlines.yml | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index f774cc86..0e626b21 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,20 @@ +- group: Goroutines + start: 03-03-2022 18:00 + deadline: 20-03-2022 23:59 + tasks: + - task: tour1 + score: 100 + - task: once + score: 100 + - task: rwmutex + score: 100 + - task: waitgroup + score: 100 + - task: cond + score: 100 + - task: ratelimit + score: 100 + - group: Interfaces start: 24-02-2022 18:00 deadline: 13-03-2022 23:59 From 872c6188fefbe7188a3481b525a8854bce26fd77 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 3 Mar 2022 10:01:38 +0300 Subject: [PATCH 07/66] Fix yaml. --- .deadlines.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.deadlines.yml b/.deadlines.yml index 0e626b21..b0a9acc4 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -11,7 +11,7 @@ - task: waitgroup score: 100 - task: cond - score: 100 + score: 100 - task: ratelimit score: 100 From 9f1c1c1d9c94ebf83d71c05efa55484bd2146b05 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Sat, 5 Mar 2022 17:02:40 +0300 Subject: [PATCH 08/66] Extend deadline. --- .deadlines.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.deadlines.yml b/.deadlines.yml index b0a9acc4..b686e35f 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,6 +1,6 @@ - group: Goroutines start: 03-03-2022 18:00 - deadline: 20-03-2022 23:59 + deadline: 22-03-2022 23:59 tasks: - task: tour1 score: 100 From 800cb4cefa86b1de20ebb0604e41f0e02e5ee9a1 Mon Sep 17 00:00:00 2001 From: Artem Garkavy Date: Sun, 6 Mar 2022 05:06:00 +0300 Subject: [PATCH 09/66] fix 29 typos --- ciletters/README.md | 2 +- cond/README.md | 2 +- distbuild/pkg/client/README.md | 4 ++-- distbuild/pkg/filecache/README.md | 2 +- distbuild/pkg/scheduler/README.md | 8 ++++---- distbuild/pkg/tarstream/README.md | 2 +- dockertest/README.md | 6 +++--- docs/build.md | 2 +- firewall/README.md | 2 +- gitfame/README.md | 8 ++++---- jsonlist/README.md | 4 ++-- once/README.md | 2 +- ratelimit/README.md | 4 ++-- rwmutex/README.md | 4 ++-- waitgroup/README.md | 4 ++-- wscat/README.md | 2 +- 16 files changed, 29 insertions(+), 29 deletions(-) diff --git a/ciletters/README.md b/ciletters/README.md index 4c8f7061..0ea42478 100644 --- a/ciletters/README.md +++ b/ciletters/README.md @@ -21,7 +21,7 @@ Нужно реализовать функцию `MakeLetter` из файла [letter.go](./letter.go), которая по go объекту нотификации генерирует её текстовое представление. -Для этого нужно написать `text/template` шаблон, сохранить его в отдлеьный файл, а затем получить его содержимое в коде с помомщью `go:embed`. +Для этого нужно написать `text/template` шаблон, сохранить его в отдельный файл, а затем получить его содержимое в коде с помомщью `go:embed`. #### Прокомментированный пример из теста ``` diff --git a/cond/README.md b/cond/README.md index 85c956de..f6091fc9 100644 --- a/cond/README.md +++ b/cond/README.md @@ -7,7 +7,7 @@ ### Что нужно сделать? -Нужно написать реализацию Cond используя каналы. +Нужно написать реализацию Cond, используя каналы. Использование пакета [sync](https://golang.org/pkg/sync) в этой задаче запрещено! diff --git a/distbuild/pkg/client/README.md b/distbuild/pkg/client/README.md index 274a5bb4..1e3d9c38 100644 --- a/distbuild/pkg/client/README.md +++ b/distbuild/pkg/client/README.md @@ -1,12 +1,12 @@ # client -Пакет `client` реализует клиента системы распределённой сборки. Клиент запускается локально, и имеет доступ к +Пакет `client` реализует клиента системы распределённой сборки. Клиент запускается локально и имеет доступ к директории с исходным кодом. Клиент получает на вход `build.Graph` и запускает сборку на координаторе. После того, как координатор создал новую сборку, клиент заливает недостающие файлы и посылает сигнал о завершении стадии заливки. -После этого, клиент следит за прогрессом сборки, дожидается завершения и выходит. +После этого клиент следит за прогрессом сборки, дожидается завершения и выходит. Клиент тестируется интеграционными тестами из пакета `disttest`. diff --git a/distbuild/pkg/filecache/README.md b/distbuild/pkg/filecache/README.md index c3dfb473..dc8f1087 100644 --- a/distbuild/pkg/filecache/README.md +++ b/distbuild/pkg/filecache/README.md @@ -12,7 +12,7 @@ - Вызов `GET /file?id=123` должен возвращать содержимое файла с `id=123`. - Вызов `PUT /file?id=123` должен заливать содержимое файла с `id=123`. -**Обратите внимание:** Несколько клиентов могут начать заливать в кеш один и тот же набор файлов. В наивной реализации, +**Обратите внимание:** Несколько клиентов могут начать заливать в кеш один и тот же набор файлов. В наивной реализации первый клиент залочит файл на запись, а следующие упадут с ошибкой. Ваш код должен обрабатывать эту ситуацию корректно, то есть последующие запросы должны дожидаться, пока первый запрос завершится. Для реализации этой логики поведения вам поможет пакет [singleflight](https://godoc.org/golang.org/x/sync/singleflight). diff --git a/distbuild/pkg/scheduler/README.md b/distbuild/pkg/scheduler/README.md index 18b8090b..5890a04e 100644 --- a/distbuild/pkg/scheduler/README.md +++ b/distbuild/pkg/scheduler/README.md @@ -15,7 +15,7 @@ воркерами. Для того, чтобы зачесть домашнее задание, достаточно реализовать упрощённый алгоритм планирования с -одной глобальной очередью. Функция `ScheduleJob` должна помещать `job` в очередь, или возвращать ссылку на существующий +одной глобальной очередью. Функция `ScheduleJob` должна помещать `job` в очередь или возвращать ссылку на существующий `pendingJob`. Функция `PickJob` должна извлекать первый элемент из очереди. Обратите внимание, что функция `PickJob` принимает контекст. Поскольку это блокирующая операция, она должна поддерживать отмены. Если вы забудете реализовать отмену в этом месте, интеграционные тесты будут зависать. @@ -30,7 +30,7 @@ 1. Одна глобальная очередь. 2. По две локальные очереди на воркер. -При запросе нового джоба воркер выбирает случайную джобу из трех очередей - глобальной, и двух локальных относящихся +При запросе нового джоба воркер выбирает случайную джобу из трех очередей - глобальной и двух локальных, относящихся к этому воркеру. Случайная очередь выбирается одним вызовом `select {}`. Ожидающий исполнения джоб всегда находится в первой локальной очереди воркеров, на которых есть @@ -41,7 +41,7 @@ из множества зависимостей этого джоба. Определения первой и второй локальной очереди не зависят от того, в каком порядке в шедулер пришли джобы -и информация о кеше артефактов. То есть, если джоб уже находится в глобальной очереди, и в этот момент приходит +и информация о кеше артефактов. То есть, если джоб уже находится в глобальной очереди и в этот момент приходит информация, что этот джоб находится в кеше на воркере `W0`, то джоб должен быть добавлен в первую локальную очередь `W0`. @@ -51,5 +51,5 @@ Вместо реального времени, юниттесты шедулера используют библиотеку `clockwork`. Это накладывает ограничения на детали вашей реализации. Ожидание `CacheTimeout` и `DepTimeout` должно быть реализовано как `select {}` на -канале, который вернула функция `TimeAfter`. Мы считаем что `CacheTimeout < DepTimeout`, и ожидание этих +канале, который вернула функция `TimeAfter`. Мы считаем, что `CacheTimeout < DepTimeout`, и ожидание этих таймаутов происходит последовательно в одной горутине. diff --git a/distbuild/pkg/tarstream/README.md b/distbuild/pkg/tarstream/README.md index e8f06c4e..8357a12f 100644 --- a/distbuild/pkg/tarstream/README.md +++ b/distbuild/pkg/tarstream/README.md @@ -1,6 +1,6 @@ # tarstream -Вам нужно уметь передавать директорию с артефактами между воркерами. Для этого, вам нужно +Вам нужно уметь передавать директорию с артефактами между воркерами. Для этого вам нужно реализовать две операции: ```go diff --git a/dockertest/README.md b/dockertest/README.md index 5360d9f0..7232814a 100644 --- a/dockertest/README.md +++ b/dockertest/README.md @@ -9,7 +9,7 @@ go test -v ./dockertest/... -count=1 ``` -Только **после того, как тесты пройдут локально** можете запушить решение в систему. +Только **после того, как тесты пройдут локально,** можете запушить решение в систему. ### С чего начать? @@ -64,7 +64,7 @@ docker-compose up Поискать решение проблемы в интернете. -Если решение найдено, и проблема выглядит общей, сделать merge request с улучшением README. +Если решение найдено и проблема выглядит общей, сделать merge request с улучшением README. Если интернет не помог, спросить в чате. @@ -82,7 +82,7 @@ docker-compose down ### Docker cheat sheet -Получить список образов +Получить список образов: ``` docker images ``` diff --git a/docs/build.md b/docs/build.md index 082c1614..f6a8e274 100644 --- a/docs/build.md +++ b/docs/build.md @@ -10,7 +10,7 @@ студентам, но будут запускаться в момент проверки решения в тестирующей системе. - При посылке решения, на сервер отправляются все файлы внутри пакета. - - При тестировании, используются изменённые файлы пакета, и + - При тестировании, используются изменённые файлы пакета и оригинальные файлы тестов. - Файл пакета можно защитить от изменения, добавив `//go:build !change` в начало файла. В этом случае при тестировании посылки всегда будет использоваться оригинальная версия файла. diff --git a/firewall/README.md b/firewall/README.md index 2ca2e157..dd1a8b15 100644 --- a/firewall/README.md +++ b/firewall/README.md @@ -2,7 +2,7 @@ В этой задаче нужно написать примитивный файрвол. -Файрвол - это прокси сервер, пропускающий через себя все запросы, +Файрвол - это прокси сервер, пропускающий через себя все запросы и отвергающий некоторые из них по заданному набору правил. Пример правил можно посмотреть в [example.yaml](./configs/example.yaml). diff --git a/gitfame/README.md b/gitfame/README.md index 8505f624..92e72cb2 100644 --- a/gitfame/README.md +++ b/gitfame/README.md @@ -30,7 +30,7 @@ f4640df4 (Fedor Korotkiy 2020-02-26 20:28:52 +0000 5) Задача считае ``` `git blame` с флагом `--porcelain` (см. `git blame --help`) возвращает информацию в машиночитаемом формате. -Кроме того, этот формат схлопывает соседние строки относящиеся к одному коммиту, +Кроме того, этот формат схлопывает соседние строки, относящиеся к одному коммиту, что может сильно сократить размер результата. Поэтому использовать нужно его. Стоит помнить, что не все файлы из директории git проекта обязательно принадлежат git репозиторию. @@ -58,7 +58,7 @@ f4640df4 (Fedor Korotkiy 2020-02-26 20:28:52 +0000 5) Задача считае **--revision** — указатель на коммит; HEAD по умолчанию -**--order-by** — ключ сортировки результатов, один из `lines` (дефолт), `commits`, `files`. +**--order-by** — ключ сортировки результатов; один из `lines` (дефолт), `commits`, `files`. По умолчанию результаты сортируются по убыванию ключа `(lines, commits, files)`. При равенстве ключей выше будет автор с лексикографически меньшим именем. @@ -116,7 +116,7 @@ ferhat elmas,1,1,1 ### Тесты -Команда для запуска тестов +Команда для запуска тестов: ``` go test -v ./gitfame/test/integration/... ``` @@ -174,7 +174,7 @@ export PATH=$GOPATH/bin:$PATH В cobra используется библиотека [pflag](https://pkg.go.dev/github.com/spf13/pflag) для работы с флагами. Библиотеку можно использовать и отдельно от cobra. `pflag` может побольше, чем стандартный [flag](https://golang.org/pkg/flag/), -в частости, в `pflag` есть полезные для решаемой задачи флаги для работы с аргументами-массивами. +в частности, в `pflag` есть полезные для решаемой задачи флаги для работы с аргументами-массивами. Помимо библиотеки, в cobra есть ещё и бинарь (с именем cobra) для кодогенерации основы проекта. diff --git a/jsonlist/README.md b/jsonlist/README.md index 8bfc6f40..3b278e8c 100644 --- a/jsonlist/README.md +++ b/jsonlist/README.md @@ -2,10 +2,10 @@ Обычные функции `json.Marshal` и `json.Unmarshal` работают с одним `json` объектом. -Иногда возникает ситуация, что вместо одного объекта, вам нужно передать последовательность объектов +Иногда возникает ситуация, что вместо одного объекта, вам нужно передать последовательность объектов, разделённых пробельными символами. Например: `{"A": 1} {"B": 2} {"C": 3}`. Такую последовательность можно прочитать используя `json.Decoder`, и можно записать используя `json.Encoder`. -Реализуйте функции `Marshal` и `Unmarshal`, которые работают со слайсом значений, и +Реализуйте функции `Marshal` и `Unmarshal`, которые работают со слайсом значений и совершают подобное преобразование. По аналогии с пакетом `json`, функция `Marshal` принимает вторым аргументом слайс, а функция `Unmarshal` - указатель на слайс. diff --git a/once/README.md b/once/README.md index db59433c..36981666 100644 --- a/once/README.md +++ b/once/README.md @@ -6,7 +6,7 @@ ### Что нужно сделать? -Нужно написать реализацию Once используя каналы. +Нужно написать реализацию Once, используя каналы. Использование пакета [sync](https://golang.org/pkg/sync) в этой задаче запрещено! diff --git a/ratelimit/README.md b/ratelimit/README.md index 610649ed..e621f90b 100644 --- a/ratelimit/README.md +++ b/ratelimit/README.md @@ -16,7 +16,7 @@ func (l *Limiter) Stop() После этого, пользователь вызывает `Acquire` из многих горутин. Некоторые из вызовов `Acquire` могут завершиться сразу, а некоторые могут заблокироваться. -`Limiter` должен гарантировать, что на любом интервале времени `interval`, не больше `maxCount` вызовов +`Limiter` должен гарантировать, что на любом интервале времени `interval` не больше `maxCount` вызовов `Acquire` могут завершиться без ошибки. Например, если `interval` равен `1s`, `maxCount` равен 100, и 200 горутин сделали вызов `Acquire` одновременно, то 100 горутин должны выйти из `Acquire` сразу, а 100 других должны заблокироваться на секунду. @@ -25,4 +25,4 @@ func (l *Limiter) Stop() во время ожидания. Об отмене `ctx` нужно узнавать по закрытию канала `ctx.Done()`. Если `ctx` отменён, нужно возвращать ошибку `ctx.Err()`. -Вызовы `Acquire()` после `Stop()`, должны сразу завершаться с ошибкой ErrStopped. +Вызовы `Acquire()` после `Stop()` должны сразу завершаться с ошибкой ErrStopped. diff --git a/rwmutex/README.md b/rwmutex/README.md index ffbd157d..7915fb9b 100644 --- a/rwmutex/README.md +++ b/rwmutex/README.md @@ -1,12 +1,12 @@ ## rwmutex [sync.RWMutex](https://golang.org/pkg/sync/#RWMutex) -- это примитив синхронизации, -предоставляющий доступ к критической секции произвольному количеству читателей, +предоставляющий доступ к критической секции произвольному количеству читателей и не более, чем одному писателю. При этом, если есть писатель, то читателей нет. ### Что нужно сделать? -Нужно написать реализацию RWMutex используя каналы. +Нужно написать реализацию RWMutex, используя каналы. Использование пакета [sync](https://golang.org/pkg/sync) в этой задаче запрещено! diff --git a/waitgroup/README.md b/waitgroup/README.md index c1253488..e479ac6a 100644 --- a/waitgroup/README.md +++ b/waitgroup/README.md @@ -4,7 +4,7 @@ ### Что нужно сделать? -Нужно написать реализацию WaitGroup используя каналы. +Нужно написать реализацию WaitGroup, используя каналы. Использование пакета [sync](https://golang.org/pkg/sync) в этой задаче запрещено! @@ -26,4 +26,4 @@ func (wg *WaitGroup) Wait() {} * Вызов `Wait` при числе большем нуля блокируется до тех пор, пока число не станет равным нулю. `WaitGroup` может быть "переиспользована". -После достижения нуля можно вызвать `Add` заблокировав последующий `Wait`. +После достижения нуля можно вызвать `Add`, заблокировав последующий `Wait`. diff --git a/wscat/README.md b/wscat/README.md index a6181092..d18ac73d 100644 --- a/wscat/README.md +++ b/wscat/README.md @@ -8,7 +8,7 @@ wscat принимает на вход единственный аргумент После подключения программа начинает читать с stdin'а и отправлять пользовательские строки на сервер, печатая все сообщения от сервера в stdout. -Клиент должен обрабатывать SIGINT и SIGTERM и плавно завершаться с кодом 0 дожидаясь горутин. +Клиент должен обрабатывать SIGINT и SIGTERM и плавно завершаться с кодом 0, дожидаясь горутин. Для этого может пригодиться [context](https://golang.org/pkg/context/). Обратите внимание на то, что exit code `go run` - это не exit code исполняемого файла. From 7c1eadce15fa9cda4810513c1b4492ab0daa285d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sun, 6 Mar 2022 00:18:51 +0000 Subject: [PATCH 10/66] fix typo in distbuild/pkg/build --- distbuild/pkg/build/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/distbuild/pkg/build/README.md b/distbuild/pkg/build/README.md index 9877a272..1ef22fe7 100644 --- a/distbuild/pkg/build/README.md +++ b/distbuild/pkg/build/README.md @@ -1,4 +1,4 @@ # build Пакет `build` содержит описание графа сборки и набор хелпер-функций для работы с графом. Вам не нужно -писать новый код в этом пакете, но нужно научиться пользоваться тем кодом который вам дан. +писать новый код в этом пакете, но нужно научиться пользоваться тем кодом, который вам дан. From 7bb153781913bd00246650a9997487335c63e5e6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sun, 6 Mar 2022 00:17:41 +0000 Subject: [PATCH 11/66] fix typo in distbuild/pkg/artifact --- distbuild/pkg/artifact/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/distbuild/pkg/artifact/README.md b/distbuild/pkg/artifact/README.md index 04ffea73..3861a9a8 100644 --- a/distbuild/pkg/artifact/README.md +++ b/distbuild/pkg/artifact/README.md @@ -13,9 +13,9 @@ `commit` помещает артефакт в кеш. `abort` отменяет запись артефакта, удаляя все данные. -После первого вызова `commit`, все последующие вызовы `commit` и `abort` должны ничего не делать. +После первого вызова `commit` все последующие вызовы `commit` и `abort` должны ничего не делать. -Точно так же, после вызова `abort`, все последующие вызовы `commit` и `abort` должны ничего не делать. +Точно так же, после вызова `abort` все последующие вызовы `commit` и `abort` должны ничего не делать. Горутина может начать читать артефакт, позвав метод `Get`. Много горутин могут читать артефакт одновременно. Горутина должна позвать `unlock`, после того как она закончила работать с артефактом. From a5129a9e8601a443211117fe908b46977d38ce11 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sun, 6 Mar 2022 00:13:46 +0000 Subject: [PATCH 12/66] fix typo in distbuild/pkg/api --- distbuild/pkg/api/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/distbuild/pkg/api/README.md b/distbuild/pkg/api/README.md index fb26e150..feced46a 100644 --- a/distbuild/pkg/api/README.md +++ b/distbuild/pkg/api/README.md @@ -18,7 +18,7 @@ Client и Coordinator общаются через два вызова. - `POST /build` - стартует новый билд. * Client посылает в Body запроса json c описанием сборки. - * Coordinator стримит в body ответа json сообщения описывающие прогресс сборки. + * Coordinator стримит в body ответа json сообщения, описывающие прогресс сборки. * Первым сообщением в ответе Coordinator присылает `buildID`. * _Тут можно было бы использовать websocket, но нас устраивает более простое решение._ From d199756e179df443a20ea27e94a83564a61d3ae3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sun, 6 Mar 2022 00:10:55 +0000 Subject: [PATCH 13/66] fix typo in distbuild --- distbuild/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/distbuild/README.md b/distbuild/README.md index e9274055..fc800bd8 100644 --- a/distbuild/README.md +++ b/distbuild/README.md @@ -66,8 +66,8 @@ type Job struct { ## Архитектура системы Наша система будет состоять из трех компонент. - * Клиент - процесс запускающий сборку. - * Воркер - процесс запускающий команды компиляции и тестирования. + * Клиент - процесс, запускающий сборку. + * Воркер - процесс, запускающий команды компиляции и тестирования. * Координатор - центральный процесс в системе, общается с клиентами и воркерами. Раздаёт задачи воркерам. From ccdef835e564eeed1dd1ab20ab384d9b5e75c913 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sun, 6 Mar 2022 00:05:48 +0000 Subject: [PATCH 14/66] fix typo in digitalclock --- digitalclock/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/digitalclock/README.md b/digitalclock/README.md index 05f917b9..ff44920a 100644 --- a/digitalclock/README.md +++ b/digitalclock/README.md @@ -94,7 +94,7 @@ go install ./digitalclock/... 3. форматирование времени: https://gobyexample.com/time-formatting-parsing 4. работа с картинками: https://golang.org/pkg/image/ -Пример, создания простой png размера 5x5: +Пример создания простой png размера 5x5: ```go package main From ebf547daf77eea64e4a219fadc0271ae865c3b85 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sat, 5 Mar 2022 23:45:34 +0000 Subject: [PATCH 15/66] fix typo in allocs --- allocs/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/allocs/README.md b/allocs/README.md index 4e83c8f1..4ddcd88b 100644 --- a/allocs/README.md +++ b/allocs/README.md @@ -3,7 +3,7 @@ `Counter` используется для нахождения уникальных слов и подсчета вхождений каждого из них. Его интерфейс выглядит так: -* `Count(r io.Reader) error` — функция, которая подсчитывает количество вхождений для каждого слова в тексте. +* `Count(r io.Reader) error` — функция, которая подсчитывает количество вхождений каждого слова в тексте. На вход подается io.Reader, в котором находится некоторый текст. Разделителями являются только переносы строк и пробелы. * `String() string` — преобразует мапу вида `{"слово": "количество вхождений"}` в форматированную строку. From f90fb44309435ff0d1a8f899fe045aa926538007 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=90=D1=80=D1=82=D1=91=D0=BC=20=D0=93=D0=B0=D1=80=D0=BA?= =?UTF-8?q?=D0=B0=D0=B2=D1=8B=D0=B9?= Date: Sat, 5 Mar 2022 19:14:43 +0000 Subject: [PATCH 16/66] improve cond_test.go --- cond/cond_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cond/cond_test.go b/cond/cond_test.go index 1337a36e..cee02e65 100644 --- a/cond/cond_test.go +++ b/cond/cond_test.go @@ -126,7 +126,7 @@ func TestCondBroadcast(t *testing.T) { // nolint func TestCondSignalStealing(t *testing.T) { - for iters := 0; iters < 1000; iters++ { + for iters := 0; iters < 20000; iters++ { var m sync.Mutex cond := New(&m) From 1d3df7c1c5265ea664d7c5d90e71b6e3a218f5f5 Mon Sep 17 00:00:00 2001 From: Covariance Date: Thu, 3 Mar 2022 12:37:25 +0000 Subject: [PATCH 17/66] Update cipher_test.go to correctly process wrapped errors via `require.ErrorIs` --- otp/cipher_test.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/otp/cipher_test.go b/otp/cipher_test.go index f84a1a71..80901b98 100644 --- a/otp/cipher_test.go +++ b/otp/cipher_test.go @@ -91,7 +91,7 @@ func TestReader(t *testing.T) { r := NewReader(testCase.r, testCase.prng) buf, err := ioutil.ReadAll(r) - require.Equal(t, testCase.err, err) + require.ErrorIs(t, err, testCase.err) require.Equal(t, testCase.result, buf) }) } @@ -139,7 +139,7 @@ func TestWriterError(t *testing.T) { n, err := w.Write(plaintext) require.Equalf(t, plaintextBackup, plaintext, "Write must not modify the slice data, even temporarily.") - require.Equal(t, err, iotest.ErrTimeout) + require.ErrorIs(t, err, iotest.ErrTimeout) require.Equal(t, 512, n) require.Equal(t, out.buf.Bytes(), ciphertext[:512]) } From 9bf3d53547d13a8b115dd65ce07a1dbacf1fc987 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 10 Mar 2022 19:54:51 +0300 Subject: [PATCH 18/66] Release testing task group. --- .deadlines.yml | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index b686e35f..d7d6da49 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,16 @@ +- group: Testing + start: 10-03-2022 22:30 + deadline: 23-03-2022 23:59 + tasks: + - task: testequal + score: 100 + - task: fileleak + score: 100 + - task: tabletest + score: 100 + - task: tparallel + score: 200 + - group: Goroutines start: 03-03-2022 18:00 deadline: 22-03-2022 23:59 From b55db12fe8649494a266a7b5ceb50f00e83eebf1 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 10 Mar 2022 20:00:30 +0300 Subject: [PATCH 19/66] Fix testing task group deadlines. --- .deadlines.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.deadlines.yml b/.deadlines.yml index d7d6da49..b23b1191 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,6 +1,6 @@ - group: Testing - start: 10-03-2022 22:30 - deadline: 23-03-2022 23:59 + start: 10-03-2022 20:00 + deadline: 29-03-2022 23:59 tasks: - task: testequal score: 100 From 952fcab12adbe89bd085a6cafa5daff84effceeb Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 10 Mar 2022 22:12:24 +0300 Subject: [PATCH 20/66] [gitfame] Improve description. --- gitfame/README.md | 53 ++++++++++++++++++++++++++++------------------- 1 file changed, 32 insertions(+), 21 deletions(-) diff --git a/gitfame/README.md b/gitfame/README.md index 92e72cb2..5fc06500 100644 --- a/gitfame/README.md +++ b/gitfame/README.md @@ -2,6 +2,27 @@ В этом задании нужно реализовать консольную утилиту для подсчёта статистик авторов git репозитория. +``` +gitfame --repository=. --extensions='.go,.md' --order-by=lines +Name Lines Commits Files +Joe Tsai 12154 92 49 +colinnewell 130 1 1 +Roger Peppe 59 1 2 +A. Ishikawa 36 1 1 +Tobias Klauser 33 1 2 +178inaba 11 2 4 +Kyle Lemons 11 1 1 +Dmitri Shuralyov 8 1 2 +ferhat elmas 7 1 4 +Christian Muehlhaeuser 6 3 4 +k.nakada 5 1 3 +LMMilewski 5 1 2 +Ernest Galbrun 3 1 1 +Ross Light 2 1 1 +Chris Morrow 1 1 1 +Fiisio 1 1 1 +``` + ### Статистики * Количество строк @@ -10,6 +31,15 @@ Все статистики считаются для состояния репозитория на момент конкретного коммита. +### Интерфейс + +Утилита должна печатать результат в stdout. +При использовании невалидного значения флага или любой другой ошибке программа должна завершаться с ненулевым кодом возврата. + +Расчёт может занимать довольно длительное время. +Хорошим качеством подобной утилиты является отображение прогресса (вынесенное за флаг). +Прогресс можно печатать в stderr в произвольном формате. + #### Расчёт Каждой строке интересующего подмножества файлов репозитория сопоставляется последний коммит, модифицировавший эту строку. @@ -41,15 +71,6 @@ f4640df4 (Fedor Korotkiy 2020-02-26 20:28:52 +0000 5) Задача считае В процессе работы скрипт не должен менять состояние репозитория ни в какой момент, поскольку с репозиторием могут параллельно работать. -### Интерфейс - -Утилита должна печатать результат в stdout. -При использовании невалидного значения флага или любой другой ошибке программа должна завершаться с ненулевым кодом возврата. - -Расчёт может занимать довольно длительное время. -Хорошим качеством подобной утилиты является отображение прогресса (вынесенное за флаг). -Прогресс можно печатать в stderr в произвольном формате. - ### Флаги Утилита должна поддерживать следующий набор флагов: @@ -124,7 +145,7 @@ go test -v ./gitfame/test/integration/... В [/tests/integration/testdata/bundles](test/integration/testdata/bundles) лежат запакованные git репозитории. Каждый интеграционный тест ссылается на какой-нибудь бандл. -Как создать bundle? Находясь в git репозитории выполнить +Как создать свой bundle? Находясь в git репозитории выполнить ``` git bundle create my.bundle --all ``` @@ -164,6 +185,7 @@ export PATH=$GOPATH/bin:$PATH В небольших проектах нет ничего плохого в том, чтобы весь код лежал плоско в корне. Здесь же, для ознакомления предлагаем изучить общепринятый подход. +В частности, писать реализацию в internal или pkg (в чём разница?). #### Cli @@ -176,17 +198,6 @@ export PATH=$GOPATH/bin:$PATH `pflag` может побольше, чем стандартный [flag](https://golang.org/pkg/flag/), в частности, в `pflag` есть полезные для решаемой задачи флаги для работы с аргументами-массивами. -Помимо библиотеки, в cobra есть ещё и бинарь (с именем cobra) для кодогенерации основы проекта. - -Его можно установить в `GOPATH` командой -``` -go get -u github.com/spf13/cobra -``` - -Генерируемый sample проект использует [viper](https://pkg.go.dev/github.com/spf13/viper) (библиотеку для работы с конфигами) и -[go-homedir](https://pkg.go.dev/github.com/mitchellh/go-homedir) (кроссплатформенную библиотеку для поиска домашней директории пользователя). -В этой задаче эти библиотеки не нужны, поэтому их нет в зависимостях проекта. - ### Git ликбез Вся информация взята из [книги](https://github.com/pluralsight/git-internals-pdf/releases/download/v2.0/peepcode-git.pdf). From ae9e830c8031e8197d4cc14d79c4ecba54f99dc2 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 10 Mar 2022 22:45:15 +0300 Subject: [PATCH 21/66] [gitfame] Improve description. --- gitfame/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gitfame/README.md b/gitfame/README.md index 5fc06500..a3c8485e 100644 --- a/gitfame/README.md +++ b/gitfame/README.md @@ -3,7 +3,7 @@ В этом задании нужно реализовать консольную утилиту для подсчёта статистик авторов git репозитория. ``` -gitfame --repository=. --extensions='.go,.md' --order-by=lines +✗ gitfame --repository=. --extensions='.go,.md' --order-by=lines Name Lines Commits Files Joe Tsai 12154 92 49 colinnewell 130 1 1 From 56c92b40e95548f1d0499c3bfc0ab427609f7550 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Fri, 11 Mar 2022 12:46:59 +0300 Subject: [PATCH 22/66] Release gitfame. --- .deadlines.yml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index b23b1191..59e20b9b 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,10 @@ +- group: "[HW] Gitfame" + start: 10-03-2022 18:00 + deadline: 29-03-2022 23:59 + tasks: + - task: gitfame + score: 0 + - group: Testing start: 10-03-2022 20:00 deadline: 29-03-2022 23:59 From 8f286860945934013657aa11185ab189bbc2dfe5 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Fri, 11 Mar 2022 12:50:21 +0300 Subject: [PATCH 23/66] Fix gitfame deadlines. --- .deadlines.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.deadlines.yml b/.deadlines.yml index 59e20b9b..8914e22f 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,6 +1,6 @@ - group: "[HW] Gitfame" - start: 10-03-2022 18:00 - deadline: 29-03-2022 23:59 + start: 11-03-2022 11:59 + deadline: 30-03-2022 23:59 tasks: - task: gitfame score: 0 From 11eaa165511ea9bfc724a38d0232b711f9c85554 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 12 Mar 2022 16:25:16 +0300 Subject: [PATCH 24/66] Run tests with race detector --- tools/testtool/commands/test_submission.go | 45 +++++++++-- .../incorrect/datarace/description.md | 1 + .../incorrect/datarace/private/.golangci.yml | 80 +++++++++++++++++++ .../datarace/private/datarace/sum.go | 8 ++ .../datarace/private/datarace/sum_solution.go | 8 ++ .../datarace/private/datarace/sum_test.go | 22 +++++ .../incorrect/datarace/private/go.mod | 9 +++ .../incorrect/datarace/private/go.sum | 53 ++++++++++++ .../datarace/student/datarace/sum.go | 26 ++++++ .../datarace/student/datarace/sum_test.go | 23 ++++++ .../incorrect/datarace/student/go.mod | 9 +++ .../incorrect/datarace/student/go.sum | 53 ++++++++++++ 12 files changed, 332 insertions(+), 5 deletions(-) create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/description.md create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/.golangci.yml create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum.go create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_solution.go create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_test.go create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/go.mod create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/private/go.sum create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum.go create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum_test.go create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/student/go.mod create mode 100644 tools/testtool/testdata/submissions/incorrect/datarace/student/go.sum diff --git a/tools/testtool/commands/test_submission.go b/tools/testtool/commands/test_submission.go index 9338b838..eb7a7349 100644 --- a/tools/testtool/commands/test_submission.go +++ b/tools/testtool/commands/test_submission.go @@ -237,8 +237,11 @@ func runTests(testDir, privateRepo, problem string) error { return cmd.Run() } - binaries := map[string]string{} - testBinaries := map[string]string{} + var ( + binaries = make(map[string]string) + testBinaries = make(map[string]string) + raceBinaries = make(map[string]string) + ) //binPkgs, testPkgs := listTestsAndBinaries(filepath.Join(testDir, problem), []string{"-tags", "private", "-mod", "readonly"}) // todo return readonly binPkgs, testPkgs := listTestsAndBinaries(filepath.Join(testDir, problem), []string{"-tags", "private"}) @@ -263,15 +266,24 @@ func runTests(testDir, privateRepo, problem string) error { binariesJSON, _ := json.Marshal(binaries) for testPkg := range testPkgs { - binPath := filepath.Join(binCache, randomName()) - testBinaries[testPkg] = binPath - cmd := []string{"test", "-mod", "readonly", "-tags", "private", "-c", "-o", binPath, testPkg} + testPath := filepath.Join(binCache, randomName()) + testBinaries[testPkg] = testPath + + cmd := []string{"test", "-mod", "readonly", "-tags", "private", "-c", "-o", testPath, testPkg} if coverageReq.Enabled { cmd = append(cmd, "-cover", "-coverpkg", strings.Join(coveragePackages, ",")) } if err := runGo(cmd...); err != nil { return fmt.Errorf("error building test in %s: %w", testPkg, err) } + + racePath := filepath.Join(binCache, randomName()) + raceBinaries[testPkg] = racePath + + cmd = []string{"test", "-mod", "readonly", "-race", "-tags", "private", "-c", "-o", racePath, testPkg} + if err := runGo(cmd...); err != nil { + return fmt.Errorf("error building test in %s: %w", testPkg, err) + } } coverProfiles := []string{} @@ -306,6 +318,29 @@ func runTests(testDir, privateRepo, problem string) error { } } + { + cmd := exec.Command(raceBinaries[testPkg], "-test.bench=.") + if currentUserIsRoot() { + if err := sandbox(cmd); err != nil { + log.Fatal(err) + } + } + + cmd.Dir = filepath.Join(testDir, relPath) + cmd.Env = []string{ + testtool.BinariesEnv + "=" + string(binariesJSON), + "PATH=" + os.Getenv("PATH"), + "HOME=" + os.Getenv("HOME"), + "GOCACHE=" + goCache, + } + cmd.Stdout = os.Stdout + cmd.Stderr = os.Stderr + + if err := cmd.Run(); err != nil { + return &TestFailedError{E: err} + } + } + { benchCmd := exec.Command(testBinary, "-test.bench=.", "-test.run=^$") if currentUserIsRoot() { diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/description.md b/tools/testtool/testdata/submissions/incorrect/datarace/description.md new file mode 100644 index 00000000..77c98504 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/description.md @@ -0,0 +1 @@ +Student solution compiles but does not pass tests. \ No newline at end of file diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/.golangci.yml b/tools/testtool/testdata/submissions/incorrect/datarace/private/.golangci.yml new file mode 100644 index 00000000..207bcb7a --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/.golangci.yml @@ -0,0 +1,80 @@ +# options for analysis running +run: + # default concurrency is a available CPU number + concurrency: 8 + + # timeout for analysis, e.g. 30s, 5m, default is 1m + deadline: 5m + + # exit code when at least one issue was found, default is 1 + issues-exit-code: 1 + + # include test files or not, default is true + tests: true + + +# output configuration options +output: + # colored-line-number|line-number|json|tab|checkstyle, default is "colored-line-number" + format: colored-line-number + + # print lines of code with issue, default is true + print-issued-lines: true + + # print linter name in the end of issue text, default is true + print-linter-name: true + + +# all available settings of specific linters +linters-settings: + govet: + # report about shadowed variables + check-shadowing: true + golint: + # minimal confidence for issues, default is 0.8 + min-confidence: 0.8 + gofmt: + # simplify code: gofmt with `-s` option, true by default + simplify: true + goimports: + # put imports beginning with prefix after 3rd-party packages; + # it's a comma-separated list of prefixes + local-prefixes: gitlab.com + stylecheck: + # https://staticcheck.io/docs/options#checks + checks: ["all", "-ST1018"] + +linters: + disable-all: true + enable: + - errcheck + - gofmt + - stylecheck + - gosimple + - govet + - ineffassign + - exportloopref + - staticcheck + - typecheck + - unconvert + + +issues: + # List of regexps of issue texts to exclude, empty list by default. + # But independently from this option we use default exclude patterns, + # it can be disabled by `exclude-use-default: false`. To list all + # excluded by default patterns execute `golangci-lint run --help` + exclude: + - Using the variable on range scope .* in function literal + + # Independently from option `exclude` we use default exclude patterns, + # it can be disabled by this option. To list all + # excluded by default patterns execute `golangci-lint run --help`. + # Default value for this option is true. + exclude-use-default: true + + # Maximum issues count per one linter. Set to 0 to disable. Default is 50. + max-per-linter: 0 + + # Maximum count of issues with the same text. Set to 0 to disable. Default is 3. + max-same-issues: 0 diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum.go b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum.go new file mode 100644 index 00000000..60b43b79 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum.go @@ -0,0 +1,8 @@ +//go:build !solution +// +build !solution + +package datarace + +func Sum(a, b int64) int64 { + return 0 +} diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_solution.go b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_solution.go new file mode 100644 index 00000000..1b780353 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_solution.go @@ -0,0 +1,8 @@ +//go:build solution +// +build solution + +package datarace + +func Sum(a, b int64) int64 { + return a + b +} diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_test.go b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_test.go new file mode 100644 index 00000000..013db3ae --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/datarace/sum_test.go @@ -0,0 +1,22 @@ +package datarace + +import ( + "math" + "testing" +) + +type testCase struct { + a, b, sum int64 +} + +func TestSum(t *testing.T) { + for _, input := range []testCase{ + {a: 2, b: 2, sum: 4}, + {a: 2, b: -2, sum: 0}, + {a: math.MaxInt64, b: 1, sum: math.MinInt64}, + } { + if out := Sum(input.a, input.b); out != input.sum { + t.Errorf("%d + %d == %d != %d", input.a, input.b, out, input.sum) + } + } +} diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/go.mod b/tools/testtool/testdata/submissions/incorrect/datarace/private/go.mod new file mode 100644 index 00000000..74beb585 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/go.mod @@ -0,0 +1,9 @@ +module gitlab.com/slon/shad-go + +go 1.16 + +require ( + github.com/spf13/cobra v0.0.5 + github.com/stretchr/testify v1.4.0 + golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825 +) diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/private/go.sum b/tools/testtool/testdata/submissions/incorrect/datarace/private/go.sum new file mode 100644 index 00000000..9d8b8ff0 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/private/go.sum @@ -0,0 +1,53 @@ +github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= +github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8= +github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= +github.com/coreos/go-etcd v2.0.0+incompatible/go.mod h1:Jez6KQU2B/sWsbdaef3ED8NzMklzPG4d5KIOhIy30Tk= +github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= +github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE= +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= +github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= +github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= +github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= +github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ= +github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= +github.com/spf13/cobra v0.0.5 h1:f0B+LkLX6DtmRH1isoNA9VTtNUK9K8xYd28JNNfOv/s= +github.com/spf13/cobra v0.0.5/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU= +github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo= +github.com/spf13/pflag v1.0.3 h1:zPAT6CGy6wXeQ7NtTnaTerfKOsV6V6F8agHXFiazDkg= +github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= +github.com/stretchr/objx v0.1.0 h1:4G4v2dO3VZwixGIRoQ5Lfboy6nUhCyYzaqnIAPPhYs4= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJyk= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= +github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= +github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= +golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= +golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/sync v0.0.0-20190423024810-112230192c58 h1:8gQV6CLnAEikrhgkHFbMAEhagSSnXWGV915qUMm9mrU= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825 h1:aNQeSIHKi0RWpKA5NO0CqyLjx6Beh5l0LLUEnndEjz0= +golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw= +gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum.go b/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum.go new file mode 100644 index 00000000..5b90bc5f --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum.go @@ -0,0 +1,26 @@ +//go:build !solution +// +build !solution + +package datarace + +import "sync" + +func Sum(a, b int64) int64 { + var s int64 + + var wg sync.WaitGroup + wg.Add(2) + + go func() { + defer wg.Done() + s += a + }() + + go func() { + defer wg.Done() + s += b + }() + + wg.Wait() + return s +} diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum_test.go b/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum_test.go new file mode 100644 index 00000000..ae0264e1 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/student/datarace/sum_test.go @@ -0,0 +1,23 @@ +package datarace + +import ( + "math" + "testing" +) + +type testCase struct { + a, b, sum int64 +} + +func TestSum(t *testing.T) { + for _, input := range []testCase{ + {a: 2, b: 2, sum: 4}, + {a: 2, b: -2, sum: 0}, + {a: math.MaxInt64, b: 1, sum: math.MinInt64}, + {a: -1, b: -1, sum: -2}, + } { + if out := Sum(input.a, input.b); out != input.sum { + t.Errorf("%d + %d == %d != %d", input.a, input.b, out, input.sum) + } + } +} diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/student/go.mod b/tools/testtool/testdata/submissions/incorrect/datarace/student/go.mod new file mode 100644 index 00000000..74beb585 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/student/go.mod @@ -0,0 +1,9 @@ +module gitlab.com/slon/shad-go + +go 1.16 + +require ( + github.com/spf13/cobra v0.0.5 + github.com/stretchr/testify v1.4.0 + golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825 +) diff --git a/tools/testtool/testdata/submissions/incorrect/datarace/student/go.sum b/tools/testtool/testdata/submissions/incorrect/datarace/student/go.sum new file mode 100644 index 00000000..9d8b8ff0 --- /dev/null +++ b/tools/testtool/testdata/submissions/incorrect/datarace/student/go.sum @@ -0,0 +1,53 @@ +github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= +github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8= +github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= +github.com/coreos/go-etcd v2.0.0+incompatible/go.mod h1:Jez6KQU2B/sWsbdaef3ED8NzMklzPG4d5KIOhIy30Tk= +github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= +github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE= +github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= +github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= +github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= +github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= +github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= +github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0= +github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= +github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= +github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= +github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= +github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g= +github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ= +github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= +github.com/spf13/cobra v0.0.5 h1:f0B+LkLX6DtmRH1isoNA9VTtNUK9K8xYd28JNNfOv/s= +github.com/spf13/cobra v0.0.5/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU= +github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo= +github.com/spf13/pflag v1.0.3 h1:zPAT6CGy6wXeQ7NtTnaTerfKOsV6V6F8agHXFiazDkg= +github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= +github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= +github.com/stretchr/objx v0.1.0 h1:4G4v2dO3VZwixGIRoQ5Lfboy6nUhCyYzaqnIAPPhYs4= +github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= +github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= +github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJyk= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= +github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= +github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= +golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= +golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= +golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/sync v0.0.0-20190423024810-112230192c58 h1:8gQV6CLnAEikrhgkHFbMAEhagSSnXWGV915qUMm9mrU= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825 h1:aNQeSIHKi0RWpKA5NO0CqyLjx6Beh5l0LLUEnndEjz0= +golang.org/x/tools v0.0.0-20200125223703-d33eef8e6825/go.mod h1:TB2adYChydJhpapKDTa4BR/hXlZSLoq2Wpct/0txZ28= +golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= +gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= +gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw= +gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= From d12ea26dfbf7d24cb6066cc5c26a1f338e52bbb9 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 15 Mar 2022 23:19:41 +0300 Subject: [PATCH 25/66] [lectures/07-sql] Some import fixes. --- lectures/07-sql/hasql/open.go | 5 ++++- lectures/07-sql/redis/redis.go | 1 + 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/lectures/07-sql/hasql/open.go b/lectures/07-sql/hasql/open.go index bfc1427a..bdc1e513 100644 --- a/lectures/07-sql/hasql/open.go +++ b/lectures/07-sql/hasql/open.go @@ -1,7 +1,10 @@ package hasql import ( + "context" + "database/sql" "log" + "time" _ "github.com/jackc/pgx/v4/stdlib" "golang.yandex/hasql" @@ -24,7 +27,7 @@ func Open() { log.Fatal(err) } - log.Println("Node address", node.Addr) + log.Println("Node address", node.Addr()) ctx, cancel := context.WithTimeout(context.Background(), time.Second) defer cancel() diff --git a/lectures/07-sql/redis/redis.go b/lectures/07-sql/redis/redis.go index fb420146..28d956c3 100644 --- a/lectures/07-sql/redis/redis.go +++ b/lectures/07-sql/redis/redis.go @@ -1,6 +1,7 @@ package redis import ( + "context" "log" "time" From da478565fbb4b8a3d365afd47cf5740c9c114478 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 15 Mar 2022 23:20:31 +0300 Subject: [PATCH 26/66] Upgrade to 1.18. --- README.md | 2 +- build.docker | 2 +- go.mod | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/README.md b/README.md index 8e1c4204..c91f208e 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # Курс по Го в ШАД -Для работы с кодом нужен go 1.17 или выше. +Для работы с кодом нужен go 1.18 или выше. ```sh git clone https://gitlab.com/slon/shad-go.git diff --git a/build.docker b/build.docker index 1bd7e70b..24a4cf5c 100644 --- a/build.docker +++ b/build.docker @@ -1,4 +1,4 @@ -FROM golang:1.17 +FROM golang:1.18 RUN apt-get update && apt-get install -y \ rsync libssl-dev \ diff --git a/go.mod b/go.mod index aa5c5f78..15928dfc 100644 --- a/go.mod +++ b/go.mod @@ -1,6 +1,6 @@ module gitlab.com/slon/shad-go -go 1.17 +go 1.18 require ( github.com/ClickHouse/clickhouse-go v1.4.0 From 28564b4257b18c2df8fb54843c84844898b8749e Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 15 Mar 2022 23:49:56 +0300 Subject: [PATCH 27/66] go fix old build tags. --- allocs/allocs.go | 1 - allocs/baseline.go | 1 - batcher/batcher.go | 1 - batcher/batcher_race_test.go | 1 - batcher/slow/value.go | 1 - blowfish/blowfish.go | 1 - ciletters/letter.go | 1 - ciletters/notification.go | 1 - cond/cond.go | 1 - coverme/app/app.go | 1 - coverme/app/coverage_test.go | 1 - coverme/client/client.go | 1 - coverme/main.go | 1 - coverme/models/storage.go | 1 - coverme/models/todo.go | 1 - coverme/utils/httputils.go | 1 - digitalclock/main.go | 1 - digitalclock/symbols.go | 1 - distbuild/pkg/api/build_client.go | 1 - distbuild/pkg/api/build_handler.go | 1 - distbuild/pkg/api/heartbeat_client.go | 1 - distbuild/pkg/api/heartbeat_handler.go | 1 - distbuild/pkg/artifact/cache.go | 1 - distbuild/pkg/artifact/client.go | 1 - distbuild/pkg/artifact/handler.go | 1 - distbuild/pkg/client/build.go | 1 - distbuild/pkg/dist/coordinator.go | 1 - distbuild/pkg/filecache/client.go | 1 - distbuild/pkg/filecache/filecache.go | 1 - distbuild/pkg/filecache/handler.go | 1 - distbuild/pkg/scheduler/scheduler.go | 1 - distbuild/pkg/tarstream/stream.go | 1 - distbuild/pkg/worker/worker.go | 1 - dupcall/dupcall.go | 1 - externalsort/io.go | 1 - externalsort/sort.go | 1 - fetchall/main.go | 1 - fetchall/main_test.go | 1 - fileleak/fileleak.go | 1 - firewall/cmd/firewall/main.go | 1 - firewall/cmd/service/main.go | 1 - forth/eval.go | 1 - forth/main.go | 1 - gitfame/cmd/gitfame/main.go | 1 - hogwarts/courselist.go | 1 - hotelbusiness/hotels.go | 1 - illegal/field.go | 1 - illegal/internal/struct.go | 1 - illegal/string.go | 1 - jsonlist/jsonlist.go | 1 - jsonrpc/jsonrpc.go | 1 - keylock/keylock.go | 1 - lrucache/cache.go | 1 - lrucache/lru.go | 1 - olympics/main.go | 1 - once/once.go | 1 - otp/cipher.go | 1 - pubsub/my_pubsub.go | 1 - pubsub/pubsub.go | 1 - ratelimit/ratelimit.go | 1 - retryupdate/kvapi/api.go | 1 - retryupdate/kvapi/errors.go | 1 - retryupdate/update.go | 1 - reversemap/reversemap.go | 1 - rwmutex/rwmutex.go | 1 - speller/speller.go | 1 - structtags/structtags.go | 1 - sum/sum.go | 1 - tabletest/coverage_test.go | 1 - tabletest/parse_duration.go | 1 - testequal/assertions.go | 1 - testequal/t.go | 1 - testifycheck/testifycheck.go | 1 - tools/testtool/buildtags.go | 1 - tparallel/tparallel.go | 1 - urlfetch/main.go | 1 - urlfetch/main_test.go | 1 - urlshortener/main.go | 1 - utf8/reverse/reverse.go | 1 - utf8/spacecollapse/collapse.go | 1 - varfmt/fmt.go | 1 - varjoin/join.go | 1 - waitgroup/waitgroup.go | 1 - wordcount/main.go | 1 - wordcount/main_test.go | 1 - wscat/main.go | 1 - 86 files changed, 86 deletions(-) diff --git a/allocs/allocs.go b/allocs/allocs.go index 86fa416d..40aa5ed5 100644 --- a/allocs/allocs.go +++ b/allocs/allocs.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package allocs diff --git a/allocs/baseline.go b/allocs/baseline.go index 402aef7d..9519382e 100644 --- a/allocs/baseline.go +++ b/allocs/baseline.go @@ -1,5 +1,4 @@ //go:build !solution && !change -// +build !solution,!change package allocs diff --git a/batcher/batcher.go b/batcher/batcher.go index 7cc4901e..84440cb2 100644 --- a/batcher/batcher.go +++ b/batcher/batcher.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package batcher diff --git a/batcher/batcher_race_test.go b/batcher/batcher_race_test.go index 0f361a65..1ac9f409 100644 --- a/batcher/batcher_race_test.go +++ b/batcher/batcher_race_test.go @@ -1,5 +1,4 @@ //go:build race -// +build race package batcher diff --git a/batcher/slow/value.go b/batcher/slow/value.go index 00f7f48a..e2e10410 100644 --- a/batcher/slow/value.go +++ b/batcher/slow/value.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package slow diff --git a/blowfish/blowfish.go b/blowfish/blowfish.go index 28a055ff..12b0890a 100644 --- a/blowfish/blowfish.go +++ b/blowfish/blowfish.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package blowfish diff --git a/ciletters/letter.go b/ciletters/letter.go index c5246adc..41304542 100644 --- a/ciletters/letter.go +++ b/ciletters/letter.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package ciletters diff --git a/ciletters/notification.go b/ciletters/notification.go index 61978e41..4c7d09fc 100644 --- a/ciletters/notification.go +++ b/ciletters/notification.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package ciletters diff --git a/cond/cond.go b/cond/cond.go index 4d74c93d..68adbc80 100644 --- a/cond/cond.go +++ b/cond/cond.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package cond diff --git a/coverme/app/app.go b/coverme/app/app.go index c9387cdc..483f6389 100644 --- a/coverme/app/app.go +++ b/coverme/app/app.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package app diff --git a/coverme/app/coverage_test.go b/coverme/app/coverage_test.go index 66b10f51..7f957c99 100644 --- a/coverme/app/coverage_test.go +++ b/coverme/app/coverage_test.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package app diff --git a/coverme/client/client.go b/coverme/client/client.go index cac5a086..793d9c8c 100644 --- a/coverme/client/client.go +++ b/coverme/client/client.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package client diff --git a/coverme/main.go b/coverme/main.go index 2c97450c..25262afc 100644 --- a/coverme/main.go +++ b/coverme/main.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/coverme/models/storage.go b/coverme/models/storage.go index 07185eeb..55df0c50 100644 --- a/coverme/models/storage.go +++ b/coverme/models/storage.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package models diff --git a/coverme/models/todo.go b/coverme/models/todo.go index 80ce4205..3e3ba52b 100644 --- a/coverme/models/todo.go +++ b/coverme/models/todo.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package models diff --git a/coverme/utils/httputils.go b/coverme/utils/httputils.go index f0527237..7cea4545 100644 --- a/coverme/utils/httputils.go +++ b/coverme/utils/httputils.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package utils diff --git a/digitalclock/main.go b/digitalclock/main.go index 375bf63c..2a10cdae 100644 --- a/digitalclock/main.go +++ b/digitalclock/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/digitalclock/symbols.go b/digitalclock/symbols.go index 6593e32f..0a33dd97 100644 --- a/digitalclock/symbols.go +++ b/digitalclock/symbols.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/distbuild/pkg/api/build_client.go b/distbuild/pkg/api/build_client.go index 77661a2d..dbd42ae2 100644 --- a/distbuild/pkg/api/build_client.go +++ b/distbuild/pkg/api/build_client.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package api diff --git a/distbuild/pkg/api/build_handler.go b/distbuild/pkg/api/build_handler.go index a682d152..0606c53e 100644 --- a/distbuild/pkg/api/build_handler.go +++ b/distbuild/pkg/api/build_handler.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package api diff --git a/distbuild/pkg/api/heartbeat_client.go b/distbuild/pkg/api/heartbeat_client.go index 7306b93c..105aab41 100644 --- a/distbuild/pkg/api/heartbeat_client.go +++ b/distbuild/pkg/api/heartbeat_client.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package api diff --git a/distbuild/pkg/api/heartbeat_handler.go b/distbuild/pkg/api/heartbeat_handler.go index a475d2d5..8daaf169 100644 --- a/distbuild/pkg/api/heartbeat_handler.go +++ b/distbuild/pkg/api/heartbeat_handler.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package api diff --git a/distbuild/pkg/artifact/cache.go b/distbuild/pkg/artifact/cache.go index a328cf8d..0d69c9d6 100644 --- a/distbuild/pkg/artifact/cache.go +++ b/distbuild/pkg/artifact/cache.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package artifact diff --git a/distbuild/pkg/artifact/client.go b/distbuild/pkg/artifact/client.go index 057ed7df..2ae9e9d1 100644 --- a/distbuild/pkg/artifact/client.go +++ b/distbuild/pkg/artifact/client.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package artifact diff --git a/distbuild/pkg/artifact/handler.go b/distbuild/pkg/artifact/handler.go index e12059f2..34c65c46 100644 --- a/distbuild/pkg/artifact/handler.go +++ b/distbuild/pkg/artifact/handler.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package artifact diff --git a/distbuild/pkg/client/build.go b/distbuild/pkg/client/build.go index 7a344871..8d018e1b 100644 --- a/distbuild/pkg/client/build.go +++ b/distbuild/pkg/client/build.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package client diff --git a/distbuild/pkg/dist/coordinator.go b/distbuild/pkg/dist/coordinator.go index 0dd73150..544762dc 100644 --- a/distbuild/pkg/dist/coordinator.go +++ b/distbuild/pkg/dist/coordinator.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package dist diff --git a/distbuild/pkg/filecache/client.go b/distbuild/pkg/filecache/client.go index 6468ace4..28408167 100644 --- a/distbuild/pkg/filecache/client.go +++ b/distbuild/pkg/filecache/client.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package filecache diff --git a/distbuild/pkg/filecache/filecache.go b/distbuild/pkg/filecache/filecache.go index 7d0ac8af..768f17f7 100644 --- a/distbuild/pkg/filecache/filecache.go +++ b/distbuild/pkg/filecache/filecache.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package filecache diff --git a/distbuild/pkg/filecache/handler.go b/distbuild/pkg/filecache/handler.go index 6a948dfb..4a271f3e 100644 --- a/distbuild/pkg/filecache/handler.go +++ b/distbuild/pkg/filecache/handler.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package filecache diff --git a/distbuild/pkg/scheduler/scheduler.go b/distbuild/pkg/scheduler/scheduler.go index 2b1a9f9d..e0260244 100644 --- a/distbuild/pkg/scheduler/scheduler.go +++ b/distbuild/pkg/scheduler/scheduler.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package scheduler diff --git a/distbuild/pkg/tarstream/stream.go b/distbuild/pkg/tarstream/stream.go index 114d12ac..b4d760b8 100644 --- a/distbuild/pkg/tarstream/stream.go +++ b/distbuild/pkg/tarstream/stream.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package tarstream diff --git a/distbuild/pkg/worker/worker.go b/distbuild/pkg/worker/worker.go index d9884b80..af06d124 100644 --- a/distbuild/pkg/worker/worker.go +++ b/distbuild/pkg/worker/worker.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package worker diff --git a/dupcall/dupcall.go b/dupcall/dupcall.go index c382e1ff..9a848b73 100644 --- a/dupcall/dupcall.go +++ b/dupcall/dupcall.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package dupcall diff --git a/externalsort/io.go b/externalsort/io.go index 012c13af..5874ea3d 100644 --- a/externalsort/io.go +++ b/externalsort/io.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package externalsort diff --git a/externalsort/sort.go b/externalsort/sort.go index 3bf00a94..b9c05b38 100644 --- a/externalsort/sort.go +++ b/externalsort/sort.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package externalsort diff --git a/fetchall/main.go b/fetchall/main.go index 375bf63c..2a10cdae 100644 --- a/fetchall/main.go +++ b/fetchall/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/fetchall/main_test.go b/fetchall/main_test.go index b63d0f41..22ba64a2 100644 --- a/fetchall/main_test.go +++ b/fetchall/main_test.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/fileleak/fileleak.go b/fileleak/fileleak.go index 38139281..1dd423b4 100644 --- a/fileleak/fileleak.go +++ b/fileleak/fileleak.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package fileleak diff --git a/firewall/cmd/firewall/main.go b/firewall/cmd/firewall/main.go index 375bf63c..2a10cdae 100644 --- a/firewall/cmd/firewall/main.go +++ b/firewall/cmd/firewall/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/firewall/cmd/service/main.go b/firewall/cmd/service/main.go index 695086bb..b59a053e 100644 --- a/firewall/cmd/service/main.go +++ b/firewall/cmd/service/main.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/forth/eval.go b/forth/eval.go index 35bd347e..e0b5d666 100644 --- a/forth/eval.go +++ b/forth/eval.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/forth/main.go b/forth/main.go index c1a87d17..63299ecd 100644 --- a/forth/main.go +++ b/forth/main.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/gitfame/cmd/gitfame/main.go b/gitfame/cmd/gitfame/main.go index 375bf63c..2a10cdae 100644 --- a/gitfame/cmd/gitfame/main.go +++ b/gitfame/cmd/gitfame/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/hogwarts/courselist.go b/hogwarts/courselist.go index 8b8750dc..34ea1409 100644 --- a/hogwarts/courselist.go +++ b/hogwarts/courselist.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package hogwarts diff --git a/hotelbusiness/hotels.go b/hotelbusiness/hotels.go index d11e9801..e0214e84 100644 --- a/hotelbusiness/hotels.go +++ b/hotelbusiness/hotels.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package hotelbusiness diff --git a/illegal/field.go b/illegal/field.go index 84eb2d09..40d26341 100644 --- a/illegal/field.go +++ b/illegal/field.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package illegal diff --git a/illegal/internal/struct.go b/illegal/internal/struct.go index 5023f2ff..c09a1b35 100644 --- a/illegal/internal/struct.go +++ b/illegal/internal/struct.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package internal diff --git a/illegal/string.go b/illegal/string.go index 3f12b3b1..2ead7435 100644 --- a/illegal/string.go +++ b/illegal/string.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package illegal diff --git a/jsonlist/jsonlist.go b/jsonlist/jsonlist.go index 8eba2c8a..98b51e3e 100644 --- a/jsonlist/jsonlist.go +++ b/jsonlist/jsonlist.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package jsonlist diff --git a/jsonrpc/jsonrpc.go b/jsonrpc/jsonrpc.go index 5ec415e9..1fe22be8 100644 --- a/jsonrpc/jsonrpc.go +++ b/jsonrpc/jsonrpc.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package jsonrpc diff --git a/keylock/keylock.go b/keylock/keylock.go index 7e21132d..7515ffbd 100644 --- a/keylock/keylock.go +++ b/keylock/keylock.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package keylock diff --git a/lrucache/cache.go b/lrucache/cache.go index 043dec72..d0f55af6 100644 --- a/lrucache/cache.go +++ b/lrucache/cache.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package lrucache diff --git a/lrucache/lru.go b/lrucache/lru.go index 357968d0..7cdaedcf 100644 --- a/lrucache/lru.go +++ b/lrucache/lru.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package lrucache diff --git a/olympics/main.go b/olympics/main.go index 375bf63c..2a10cdae 100644 --- a/olympics/main.go +++ b/olympics/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/once/once.go b/once/once.go index 28d206fb..eec3c92d 100644 --- a/once/once.go +++ b/once/once.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package once diff --git a/otp/cipher.go b/otp/cipher.go index dafcb2f0..993ab22b 100644 --- a/otp/cipher.go +++ b/otp/cipher.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package otp diff --git a/pubsub/my_pubsub.go b/pubsub/my_pubsub.go index 81b7d6a0..9ab8cc2e 100644 --- a/pubsub/my_pubsub.go +++ b/pubsub/my_pubsub.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package pubsub diff --git a/pubsub/pubsub.go b/pubsub/pubsub.go index cae35655..0c68472b 100644 --- a/pubsub/pubsub.go +++ b/pubsub/pubsub.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package pubsub diff --git a/ratelimit/ratelimit.go b/ratelimit/ratelimit.go index 8ebca196..1c2a2f5f 100644 --- a/ratelimit/ratelimit.go +++ b/ratelimit/ratelimit.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package ratelimit diff --git a/retryupdate/kvapi/api.go b/retryupdate/kvapi/api.go index 0ce5baed..f05b61ee 100644 --- a/retryupdate/kvapi/api.go +++ b/retryupdate/kvapi/api.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package kvapi diff --git a/retryupdate/kvapi/errors.go b/retryupdate/kvapi/errors.go index 28599d25..a5920a9d 100644 --- a/retryupdate/kvapi/errors.go +++ b/retryupdate/kvapi/errors.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package kvapi diff --git a/retryupdate/update.go b/retryupdate/update.go index 42ade378..a404f18a 100644 --- a/retryupdate/update.go +++ b/retryupdate/update.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package retryupdate diff --git a/reversemap/reversemap.go b/reversemap/reversemap.go index b7a99cc0..0572a702 100644 --- a/reversemap/reversemap.go +++ b/reversemap/reversemap.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package reversemap diff --git a/rwmutex/rwmutex.go b/rwmutex/rwmutex.go index 2a7b5619..4156b5e5 100644 --- a/rwmutex/rwmutex.go +++ b/rwmutex/rwmutex.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package rwmutex diff --git a/speller/speller.go b/speller/speller.go index 0e4d1140..b1f50f58 100644 --- a/speller/speller.go +++ b/speller/speller.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package speller diff --git a/structtags/structtags.go b/structtags/structtags.go index 091f9520..b2e8625e 100644 --- a/structtags/structtags.go +++ b/structtags/structtags.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package structtags diff --git a/sum/sum.go b/sum/sum.go index 3ae5e2d5..1da0e52c 100644 --- a/sum/sum.go +++ b/sum/sum.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package sum diff --git a/tabletest/coverage_test.go b/tabletest/coverage_test.go index 6fc9f693..34d85dc4 100644 --- a/tabletest/coverage_test.go +++ b/tabletest/coverage_test.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package tabletest diff --git a/tabletest/parse_duration.go b/tabletest/parse_duration.go index f60fe08e..af46f1ba 100644 --- a/tabletest/parse_duration.go +++ b/tabletest/parse_duration.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package tabletest diff --git a/testequal/assertions.go b/testequal/assertions.go index b73260fb..1f4a1b15 100644 --- a/testequal/assertions.go +++ b/testequal/assertions.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package testequal diff --git a/testequal/t.go b/testequal/t.go index 0d485cf0..9d96c411 100644 --- a/testequal/t.go +++ b/testequal/t.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package testequal diff --git a/testifycheck/testifycheck.go b/testifycheck/testifycheck.go index d7886bcc..3cd54002 100644 --- a/testifycheck/testifycheck.go +++ b/testifycheck/testifycheck.go @@ -1,4 +1,3 @@ //go:build !solution -// +build !solution package testifycheck diff --git a/tools/testtool/buildtags.go b/tools/testtool/buildtags.go index a9d9de39..464aea1e 100644 --- a/tools/testtool/buildtags.go +++ b/tools/testtool/buildtags.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package testtool diff --git a/tparallel/tparallel.go b/tparallel/tparallel.go index a1bd3954..56091a13 100644 --- a/tparallel/tparallel.go +++ b/tparallel/tparallel.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package tparallel diff --git a/urlfetch/main.go b/urlfetch/main.go index 375bf63c..2a10cdae 100644 --- a/urlfetch/main.go +++ b/urlfetch/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/urlfetch/main_test.go b/urlfetch/main_test.go index e5351342..c02af548 100644 --- a/urlfetch/main_test.go +++ b/urlfetch/main_test.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/urlshortener/main.go b/urlshortener/main.go index 375bf63c..2a10cdae 100644 --- a/urlshortener/main.go +++ b/urlshortener/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/utf8/reverse/reverse.go b/utf8/reverse/reverse.go index 885ff352..38d066c4 100644 --- a/utf8/reverse/reverse.go +++ b/utf8/reverse/reverse.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package reverse diff --git a/utf8/spacecollapse/collapse.go b/utf8/spacecollapse/collapse.go index 34b21b8b..2af12440 100644 --- a/utf8/spacecollapse/collapse.go +++ b/utf8/spacecollapse/collapse.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package spacecollapse diff --git a/varfmt/fmt.go b/varfmt/fmt.go index 50396c1d..b093e45a 100644 --- a/varfmt/fmt.go +++ b/varfmt/fmt.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package varfmt diff --git a/varjoin/join.go b/varjoin/join.go index 39e658f0..e58f5cab 100644 --- a/varjoin/join.go +++ b/varjoin/join.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package varjoin diff --git a/waitgroup/waitgroup.go b/waitgroup/waitgroup.go index 6925be02..5d2b14a4 100644 --- a/waitgroup/waitgroup.go +++ b/waitgroup/waitgroup.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package waitgroup diff --git a/wordcount/main.go b/wordcount/main.go index 375bf63c..2a10cdae 100644 --- a/wordcount/main.go +++ b/wordcount/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main diff --git a/wordcount/main_test.go b/wordcount/main_test.go index f29734c5..41ddb805 100644 --- a/wordcount/main_test.go +++ b/wordcount/main_test.go @@ -1,5 +1,4 @@ //go:build !change -// +build !change package main diff --git a/wscat/main.go b/wscat/main.go index 375bf63c..2a10cdae 100644 --- a/wscat/main.go +++ b/wscat/main.go @@ -1,5 +1,4 @@ //go:build !solution -// +build !solution package main From 56792247b9a07c3f1f99310d49cfe93ae4d2b49b Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 17 Mar 2022 23:59:54 +0300 Subject: [PATCH 28/66] Release concurrency. --- .deadlines.yml | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index 8914e22f..e0059622 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,16 @@ +- group: Concurrency with shared memory + start: 17-03-2022 23:59 + deadline: 03-04-2022 23:59 + tasks: + - task: dupcall + score: 200 + - task: keylock + score: 200 + - task: batcher + score: 200 + - task: pubsub + score: 300 + - group: "[HW] Gitfame" start: 11-03-2022 11:59 deadline: 30-03-2022 23:59 From cd018e9f4a9dcb4c8b4cc1a2c97650b05115ade9 Mon Sep 17 00:00:00 2001 From: Sergei Kozunov Date: Wed, 16 Mar 2022 21:04:38 +0000 Subject: [PATCH 29/66] Update lecture.slide byte = 8bits --- lectures/01-basics/lecture.slide | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lectures/01-basics/lecture.slide b/lectures/01-basics/lecture.slide index 9496adff..8aeef12a 100644 --- a/lectures/01-basics/lecture.slide +++ b/lectures/01-basics/lecture.slide @@ -242,10 +242,10 @@ Кодировка utf8 - 0xxxxxx runes 0−127 - 11xxxxx 10xxxxxx 128−2047 - 110xxxx 10xxxxxx 10xxxxxx 2048−65535 - 1110xxx 10xxxxxx 10xxxxxx 10xxxxxx 65536−0x10ffff + 0xxxxxxx runes 0−127 + 110xxxxx 10xxxxxx 128−2047 + 1110xxxx 10xxxxxx 10xxxxxx 2048−65535 + 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx 65536−0x10ffff Разница между рунами и байтами From d77ae964642c67f916377d83d80d4471bad6d667 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Fri, 18 Mar 2022 20:06:50 +0000 Subject: [PATCH 30/66] Update keylock/speed_test.go --- keylock/speed_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/keylock/speed_test.go b/keylock/speed_test.go index 42a44ac6..1c452e14 100644 --- a/keylock/speed_test.go +++ b/keylock/speed_test.go @@ -70,7 +70,7 @@ func BenchmarkKeyLock_NoBusyWait(b *testing.B) { cancel := make(chan struct{}) defer close(cancel) - for i := 0; i < 10000; i++ { + for i := 0; i < 5000; i++ { go func() { l.LockKeys(lockedKey, cancel) }() From 6895b42808307f680d1ce38b86d19b0ebd19aa95 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Fri, 18 Mar 2022 23:25:42 +0300 Subject: [PATCH 31/66] Fix --- keylock/speed_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/keylock/speed_test.go b/keylock/speed_test.go index 1c452e14..74831938 100644 --- a/keylock/speed_test.go +++ b/keylock/speed_test.go @@ -70,7 +70,7 @@ func BenchmarkKeyLock_NoBusyWait(b *testing.B) { cancel := make(chan struct{}) defer close(cancel) - for i := 0; i < 5000; i++ { + for i := 0; i < 1000; i++ { go func() { l.LockKeys(lockedKey, cancel) }() From b0739ad9188f836599c7cfd62085969832030486 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Mar 2022 17:07:39 +0300 Subject: [PATCH 32/66] Release http. --- .deadlines.yml | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index e0059622..9bae0951 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,18 @@ +- group: HTTP + start: 23-03-2022 18:00 + deadline: 10-04-2022 23:59 + tasks: + - task: urlshortener + score: 100 + - task: digitalclock + score: 100 + - task: coverme + score: 200 + - task: olympics + score: 200 + - task: firewall + score: 200 + - group: Concurrency with shared memory start: 17-03-2022 23:59 deadline: 03-04-2022 23:59 From 8868dac428d9d5611a458818a20ae369b7c42c0b Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Mar 2022 18:48:48 +0300 Subject: [PATCH 33/66] [coverme] Add finish todo handler. --- coverme/README.md | 22 +++++++++++++++++++--- coverme/app/app.go | 27 +++++++++++++++++++++------ coverme/client/client.go | 16 ++++++++++++++++ coverme/models/storage.go | 14 ++++++++++++++ 4 files changed, 70 insertions(+), 9 deletions(-) diff --git a/coverme/README.md b/coverme/README.md index 0efcaa24..042c2f54 100644 --- a/coverme/README.md +++ b/coverme/README.md @@ -44,7 +44,7 @@ Todo-app с минимальной функциональностью + client. Health check: ``` -✗ curl -i -X GET localhost:6029/ +✗ curl -i -X GET localhost:6029/ HTTP/1.1 200 OK Content-Type: application/json Date: Thu, 19 Mar 2020 21:46:02 GMT @@ -66,7 +66,7 @@ Content-Length: 51 Получить todo по id: ``` -✗ curl -i localhost:6029/todo/0 +✗ curl -i localhost:6029/todo/0 HTTP/1.1 200 OK Content-Type: application/json Date: Thu, 19 Mar 2020 21:44:17 GMT @@ -77,7 +77,7 @@ Content-Length: 51 Получить все todo: ``` -✗ curl -i -X GET localhost:6029/todo +✗ curl -i -X GET localhost:6029/todo HTTP/1.1 200 OK Content-Type: application/json Date: Thu, 19 Mar 2020 21:44:37 GMT @@ -85,3 +85,19 @@ Content-Length: 53 [{"id":0,"title":"A","content":"a","finished":false}] ``` + +Завершить todo: +``` +✗ curl -i -X POST localhost:6029/todo/0/finish +HTTP/1.1 200 OK +Date: Thu, 24 Mar 2022 15:40:49 GMT +Content-Length: 0 + +✗ curl -i -X GET localhost:6029/todo +HTTP/1.1 200 OK +Content-Type: application/json +Date: Thu, 24 Mar 2022 15:41:04 GMT +Content-Length: 52 + +[{"id":0,"title":"A","content":"a","finished":true}]% +``` diff --git a/coverme/app/app.go b/coverme/app/app.go index c9387cdc..22d39b6c 100644 --- a/coverme/app/app.go +++ b/coverme/app/app.go @@ -9,7 +9,6 @@ import ( "net/http" "os" "strconv" - "strings" "github.com/gorilla/handlers" "github.com/gorilla/mux" @@ -34,10 +33,11 @@ func (app *App) Start(port int) { func (app *App) initRoutes() { app.router = mux.NewRouter() - app.router.HandleFunc("/", app.status).Methods("Get") - app.router.HandleFunc("/todo", app.list).Methods("Get") - app.router.HandleFunc("/todo/{id:[0-9]+}", app.getTodo).Methods("Get") - app.router.HandleFunc("/todo/create", app.addTodo).Methods("Post") + app.router.HandleFunc("/", app.status).Methods("GET") + app.router.HandleFunc("/todo", app.list).Methods("GET") + app.router.HandleFunc("/todo/{id:[0-9]+}", app.getTodo).Methods("GET") + app.router.HandleFunc("/todo/{id:[0-9]+}/finish", app.finishTodo).Methods("POST") + app.router.HandleFunc("/todo/create", app.addTodo).Methods("POST") } func (app *App) run(addr string) { @@ -80,7 +80,7 @@ func (app *App) addTodo(w http.ResponseWriter, r *http.Request) { } func (app *App) getTodo(w http.ResponseWriter, r *http.Request) { - id, err := strconv.Atoi(strings.TrimPrefix(r.URL.Path, "/todo/")) + id, err := strconv.Atoi(mux.Vars(r)["id"]) if err != nil { utils.BadRequest(w, "ID must be an int") return @@ -95,6 +95,21 @@ func (app *App) getTodo(w http.ResponseWriter, r *http.Request) { _ = utils.RespondJSON(w, http.StatusOK, todo) } +func (app *App) finishTodo(w http.ResponseWriter, r *http.Request) { + id, err := strconv.Atoi(mux.Vars(r)["id"]) + if err != nil { + utils.BadRequest(w, "ID must be an int") + return + } + + if err := app.db.FinishTodo(models.ID(id)); err != nil { + utils.ServerError(w) + return + } + + w.WriteHeader(http.StatusOK) +} + func (app *App) status(w http.ResponseWriter, r *http.Request) { _ = utils.RespondJSON(w, http.StatusOK, "API is up and working!") } diff --git a/coverme/client/client.go b/coverme/client/client.go index cac5a086..b3bbe225 100644 --- a/coverme/client/client.go +++ b/coverme/client/client.go @@ -69,3 +69,19 @@ func (c *Client) List() ([]*models.Todo, error) { err = json.NewDecoder(resp.Body).Decode(&todos) return todos, err } + +func (c *Client) Finish(id models.ID) error { + u := fmt.Sprintf("%s/todo/%d/finish", c.addr, id) + + resp, err := http.Post(u, "application/json", nil) + if err != nil { + return err + } + defer func() { _ = resp.Body.Close() }() + + if resp.StatusCode != http.StatusOK { + return fmt.Errorf("unexpected status code %d", resp.StatusCode) + } + + return err +} diff --git a/coverme/models/storage.go b/coverme/models/storage.go index 07185eeb..c4fc9815 100644 --- a/coverme/models/storage.go +++ b/coverme/models/storage.go @@ -12,6 +12,7 @@ type Storage interface { AddTodo(string, string) (*Todo, error) GetTodo(ID) (*Todo, error) GetAll() ([]*Todo, error) + FinishTodo(ID) error } type InMemoryStorage struct { @@ -69,3 +70,16 @@ func (s *InMemoryStorage) GetAll() ([]*Todo, error) { return out, nil } + +func (s *InMemoryStorage) FinishTodo(id ID) error { + s.mu.Lock() + defer s.mu.Unlock() + + todo, ok := s.todos[id] + if !ok { + return fmt.Errorf("todo %d not found", id) + } + + todo.MarkFinished() + return nil +} From 52d82909561864807544b7d285c970a24c7534ac Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Mar 2022 18:49:56 +0300 Subject: [PATCH 34/66] [coverme] Update readme. --- coverme/README.md | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/coverme/README.md b/coverme/README.md index 042c2f54..a4243e0b 100644 --- a/coverme/README.md +++ b/coverme/README.md @@ -16,12 +16,18 @@ Package main можно не тестировать. Coverage 100% говорит ровно о том, что все строки кода выполнялись. Хорошие тесты, в первую очередь, тестируют функциональность. -Как посмотреть coverage: +Как посмотреть общий coverage: ``` go test -v -cover ./coverme/... ``` -Coverage можно выводить в html (см. ссылки), и эта функциональность поддерживается в Goland. +Как посмотреть coverage пакета в html: +``` +go test -v -coverprofile=/tmp/coverage.out ./coverme/models/... +go tool cover -html=/tmp/coverage.out +``` +Аналогичная функциональность поддерживается в Goland. +Также рекомендуем ознакомиться с рассказом о cover в блоге (см. ссылки). ## Ссылки From 1bdf9f18a5507c30477487d741f00d9cf09a39de Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 24 Mar 2022 18:51:08 +0300 Subject: [PATCH 35/66] Inc coverme points. --- .deadlines.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.deadlines.yml b/.deadlines.yml index 9bae0951..26539e0f 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -6,12 +6,12 @@ score: 100 - task: digitalclock score: 100 - - task: coverme - score: 200 - task: olympics score: 200 - task: firewall score: 200 + - task: coverme + score: 300 - group: Concurrency with shared memory start: 17-03-2022 23:59 From ad928156a22e86a705afcedd32ccde37c70014d2 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Fri, 25 Mar 2022 16:13:39 +0300 Subject: [PATCH 36/66] [gitfame] Fix readme. --- gitfame/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gitfame/README.md b/gitfame/README.md index a3c8485e..ed8670e0 100644 --- a/gitfame/README.md +++ b/gitfame/README.md @@ -218,7 +218,7 @@ export PATH=$GOPATH/bin:$PATH **branch** (ветка) — это не объект `Git Object Database`, а всего лишь файл в директории `.git/refs/heads/` с хэшом последнего для этой ветки коммита. То есть ветка — это указатель на коммит. -**head** — это ссылка на коммит. В каждом репозитории по умолчанию есть **head** именем **master**. +**head** — это ссылка на коммит. В каждом репозитории по умолчанию есть **head** с именем **master**. **HEAD** — один выделенный **head**. Файл `.git/HEAD`. Родитель следующего коммита. From aab64fa618878eb3097834a6162984a40a55af84 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 15:52:25 +0300 Subject: [PATCH 37/66] Start local postgres server --- build.docker | 2 +- pgfixture/pg.go | 63 ++++++++++++++++++++++++++++++++++++++++++++ pgfixture/pg_test.go | 34 ++++++++++++++++++++++++ 3 files changed, 98 insertions(+), 1 deletion(-) create mode 100644 pgfixture/pg.go create mode 100644 pgfixture/pg_test.go diff --git a/build.docker b/build.docker index 1bd7e70b..fdec5125 100644 --- a/build.docker +++ b/build.docker @@ -1,7 +1,7 @@ FROM golang:1.17 RUN apt-get update && apt-get install -y \ - rsync libssl-dev \ + rsync libssl-dev postgresql \ && rm -rf /var/lib/apt/lists/* RUN curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v1.44.0 diff --git a/pgfixture/pg.go b/pgfixture/pg.go new file mode 100644 index 00000000..c4f36228 --- /dev/null +++ b/pgfixture/pg.go @@ -0,0 +1,63 @@ +package pgfixture + +import ( + "fmt" + "os" + "os/exec" + "testing" + "time" +) + +func Start(t *testing.T) string { + pgconn, ok := os.LookupEnv("PGCONN") + if ok { + t.Logf("using external database: PGCONN=%s", pgconn) + return pgconn + } + + _, err := exec.LookPath("initdb") + if err != nil { + t.Fatalf("initdb binary not found; is postgres installed?") + } + + _, err = exec.LookPath("postgres") + if err != nil { + t.Fatalf("postgres binary not found; is postgres installed?") + } + + pgdata := t.TempDir() + + cmd := exec.Command("initdb", "-N", "-D", pgdata) + cmd.Stderr = os.Stderr + cmd.Stdout = os.Stdout + if err := cmd.Run(); err != nil { + t.Fatalf("initdb failed: %v", err) + } + + pgrun := t.TempDir() + + cmd = exec.Command("postgres", "-D", pgdata, "-k", pgrun, "-F") + cmd.Stderr = os.Stderr + cmd.Stdout = os.Stdout + if err := cmd.Start(); err != nil { + t.Fatalf("postgres failed: %v", err) + } + + finished := make(chan error, 1) + go func() { + finished <- cmd.Wait() + }() + + select { + case <-finished: + t.Fatalf("postgres server terminated: %v", err) + + case <-time.After(time.Second / 2): + } + + t.Cleanup(func() { + _ = cmd.Process.Kill() + }) + + return fmt.Sprintf("host=%s database=postgres", pgrun) +} diff --git a/pgfixture/pg_test.go b/pgfixture/pg_test.go new file mode 100644 index 00000000..e2d56128 --- /dev/null +++ b/pgfixture/pg_test.go @@ -0,0 +1,34 @@ +package pgfixture_test + +import ( + "context" + "testing" + + "github.com/jackc/pgx/v4" + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/pgfixture" +) + +func TestLocalPostgres(t *testing.T) { + dsn := pgfixture.Start(t) + ctx := context.Background() + + conn, err := pgx.Connect(ctx, dsn) + require.NoError(t, err) + require.NoError(t, conn.Ping(ctx)) + + _, err = conn.Exec(ctx, `CREATE TABLE users (id SERIAL PRIMARY KEY, name TEXT);`) + require.NoError(t, err) + + _, err = conn.Exec(ctx, `INSERT INTO users (name) VALUES ($1);`, "Fedor") + require.NoError(t, err) + + row := conn.QueryRow(ctx, `SELECT id, name FROM users LIMIT 1;`) + + var id int + var name string + + require.NoError(t, row.Scan(&id, &name)) + require.Equal(t, 1, id) + require.Equal(t, name, "Fedor") +} From e410636456f62c77147faf4fe178a69987d229e0 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 16:01:06 +0300 Subject: [PATCH 38/66] Fix linter error --- pgfixture/pg.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pgfixture/pg.go b/pgfixture/pg.go index c4f36228..7bd5ff10 100644 --- a/pgfixture/pg.go +++ b/pgfixture/pg.go @@ -30,7 +30,7 @@ func Start(t *testing.T) string { cmd := exec.Command("initdb", "-N", "-D", pgdata) cmd.Stderr = os.Stderr cmd.Stdout = os.Stdout - if err := cmd.Run(); err != nil { + if err = cmd.Run(); err != nil { t.Fatalf("initdb failed: %v", err) } @@ -39,7 +39,7 @@ func Start(t *testing.T) string { cmd = exec.Command("postgres", "-D", pgdata, "-k", pgrun, "-F") cmd.Stderr = os.Stderr cmd.Stdout = os.Stdout - if err := cmd.Start(); err != nil { + if err = cmd.Start(); err != nil { t.Fatalf("postgres failed: %v", err) } From 44c47db9b2c077a61b657c9266bea7b0a127bee7 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 16:12:29 +0300 Subject: [PATCH 39/66] Adapt for ubuntu --- pgfixture/pg.go | 46 +++++++++++++++++++++++++++++++--------------- 1 file changed, 31 insertions(+), 15 deletions(-) diff --git a/pgfixture/pg.go b/pgfixture/pg.go index 7bd5ff10..8b2d3a28 100644 --- a/pgfixture/pg.go +++ b/pgfixture/pg.go @@ -2,12 +2,38 @@ package pgfixture import ( "fmt" + "io/ioutil" "os" "os/exec" + "path/filepath" "testing" "time" ) +func lookPath(t *testing.T, name string) string { + t.Helper() + + path, err := exec.LookPath(name) + if err == nil { + return path + } + + const ubuntuPostgres = "/usr/lib/postgresql" + + if dirs, err := ioutil.ReadDir(ubuntuPostgres); err == nil { + for _, d := range dirs { + path := filepath.Join(ubuntuPostgres, d.Name(), "bin", name) + + if _, err := os.Stat(path); err == nil { + return path + } + } + } + + t.Fatalf("%s binary not found; is postgres installed?", name) + return "" +} + func Start(t *testing.T) string { pgconn, ok := os.LookupEnv("PGCONN") if ok { @@ -15,31 +41,21 @@ func Start(t *testing.T) string { return pgconn } - _, err := exec.LookPath("initdb") - if err != nil { - t.Fatalf("initdb binary not found; is postgres installed?") - } - - _, err = exec.LookPath("postgres") - if err != nil { - t.Fatalf("postgres binary not found; is postgres installed?") - } - pgdata := t.TempDir() - cmd := exec.Command("initdb", "-N", "-D", pgdata) + cmd := exec.Command(lookPath(t, "initdb"), "-N", "-D", pgdata) cmd.Stderr = os.Stderr cmd.Stdout = os.Stdout - if err = cmd.Run(); err != nil { + if err := cmd.Run(); err != nil { t.Fatalf("initdb failed: %v", err) } pgrun := t.TempDir() - cmd = exec.Command("postgres", "-D", pgdata, "-k", pgrun, "-F") + cmd = exec.Command(lookPath(t, "postgres"), "-D", pgdata, "-k", pgrun, "-F") cmd.Stderr = os.Stderr cmd.Stdout = os.Stdout - if err = cmd.Start(); err != nil { + if err := cmd.Start(); err != nil { t.Fatalf("postgres failed: %v", err) } @@ -49,7 +65,7 @@ func Start(t *testing.T) string { }() select { - case <-finished: + case err := <-finished: t.Fatalf("postgres server terminated: %v", err) case <-time.After(time.Second / 2): From de61b1f8683c86aeb9ac953acd36bd6fb814c348 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 16:52:58 +0300 Subject: [PATCH 40/66] Run tests from nobody --- .releaser-ci.yml | 4 ++-- build.docker | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.releaser-ci.yml b/.releaser-ci.yml index 034ff87b..33a040fd 100644 --- a/.releaser-ci.yml +++ b/.releaser-ci.yml @@ -11,8 +11,8 @@ check: - golangci-lint run --build-tags private,solution ./... #- go test -v -tags private,solution ./... #- go test -v -race -tags private,solution ./... - - go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... - - go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... + - sudo -u nobody go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... + - sudo -u nobody go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... rebuild-base-image: tags: diff --git a/build.docker b/build.docker index fdec5125..5dc4cec1 100644 --- a/build.docker +++ b/build.docker @@ -1,7 +1,7 @@ FROM golang:1.17 RUN apt-get update && apt-get install -y \ - rsync libssl-dev postgresql \ + rsync libssl-dev postgresql sudo \ && rm -rf /var/lib/apt/lists/* RUN curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v1.44.0 From cd9b8d290563a71ef4a7b6939209c6c7d48c56b3 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 16:56:05 +0300 Subject: [PATCH 41/66] Pass PATH to sudo --- .releaser-ci.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.releaser-ci.yml b/.releaser-ci.yml index 33a040fd..f01b4ff1 100644 --- a/.releaser-ci.yml +++ b/.releaser-ci.yml @@ -11,8 +11,8 @@ check: - golangci-lint run --build-tags private,solution ./... #- go test -v -tags private,solution ./... #- go test -v -race -tags private,solution ./... - - sudo -u nobody go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... - - sudo -u nobody go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... + - sudo -u nobody PATH=$PATH go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... + - sudo -u nobody PATH=$PATH go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... rebuild-base-image: tags: From 3007a29a8c5345d8a74e7a0b012ff533d8648bae Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 16:57:50 +0300 Subject: [PATCH 42/66] Use absolute go path --- .releaser-ci.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.releaser-ci.yml b/.releaser-ci.yml index f01b4ff1..122784d3 100644 --- a/.releaser-ci.yml +++ b/.releaser-ci.yml @@ -11,8 +11,8 @@ check: - golangci-lint run --build-tags private,solution ./... #- go test -v -tags private,solution ./... #- go test -v -race -tags private,solution ./... - - sudo -u nobody PATH=$PATH go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... - - sudo -u nobody PATH=$PATH go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... + - sudo -u nobody PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... + - sudo -u nobody PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... rebuild-base-image: tags: From 1fcb89a4c6d7f3595f3a9fc10e5d809570e6e968 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 17:00:12 +0300 Subject: [PATCH 43/66] Try fixing go --- .releaser-ci.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.releaser-ci.yml b/.releaser-ci.yml index 122784d3..a30714a5 100644 --- a/.releaser-ci.yml +++ b/.releaser-ci.yml @@ -11,8 +11,8 @@ check: - golangci-lint run --build-tags private,solution ./... #- go test -v -tags private,solution ./... #- go test -v -race -tags private,solution ./... - - sudo -u nobody PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... - - sudo -u nobody PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... + - sudo -u nobody HOME=/tmp PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest | grep -v /foolsday3) -tags private,solution -v ./... + - sudo -u nobody HOME=/tmp PATH=$PATH /usr/local/go/bin/go test $(go list -tags private,solution ./... | grep -v /dockertest) -tags private,solution -v -race ./... rebuild-base-image: tags: From 293bce6150e3dc5161ff1b4b21c98dde5e992913 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 26 Mar 2022 20:41:17 +0300 Subject: [PATCH 44/66] Add dao. Simple sql task. --- dao/README.md | 10 +++++++++ dao/dao.go | 9 ++++++++ dao/dao_test.go | 55 +++++++++++++++++++++++++++++++++++++++++++++++++ dao/model.go | 22 ++++++++++++++++++++ 4 files changed, 96 insertions(+) create mode 100644 dao/README.md create mode 100644 dao/dao.go create mode 100644 dao/dao_test.go create mode 100644 dao/model.go diff --git a/dao/README.md b/dao/README.md new file mode 100644 index 00000000..97258111 --- /dev/null +++ b/dao/README.md @@ -0,0 +1,10 @@ +# dao + +В этой задаче вам нужно реализовать data access object для доступа к таблице пользователей. + +- Функция `CreateDao` должна создавать таблицу в базе данных. +- Метод `Create` должен создавать нового пользователя и назначать его `ID`. +- Метод `Update` меняет `Name` пользователя. +- Метод `Delete` удаляет пользователя из таблицы. +- Метод `Lookup` возвращает `Name` пользователя по `ID`. +- Метод `List` возвращает список все пользователей в таблице. diff --git a/dao/dao.go b/dao/dao.go new file mode 100644 index 00000000..4cadf5ea --- /dev/null +++ b/dao/dao.go @@ -0,0 +1,9 @@ +//go:build !solution + +package dao + +import "context" + +func CreateDao(ctx context.Context, dsn string) (Dao, error) { + panic("not implemented") +} diff --git a/dao/dao_test.go b/dao/dao_test.go new file mode 100644 index 00000000..ebb1a4fe --- /dev/null +++ b/dao/dao_test.go @@ -0,0 +1,55 @@ +package dao + +import ( + "context" + "database/sql" + "sort" + "testing" + + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/pgfixture" +) + +func TestDao(t *testing.T) { + dsn := pgfixture.Start(t) + + ctx := context.Background() + + dao, err := CreateDao(ctx, dsn) + require.NoError(t, err) + + _, err = dao.Lookup(ctx, 42) + require.ErrorIs(t, err, sql.ErrNoRows) + + aliceID, err := dao.Create(ctx, &User{Name: "Alice"}) + require.NoError(t, err) + bobID, err := dao.Create(ctx, &User{Name: "Bob"}) + require.NoError(t, err) + charlieID, err := dao.Create(ctx, &User{Name: "Charie"}) + require.NoError(t, err) + + require.Len(t, map[UserID]struct{}{aliceID: {}, bobID: {}, charlieID: {}}, 3) + + alice, err := dao.Lookup(ctx, aliceID) + require.NoError(t, err) + require.Equal(t, alice, User{ID: aliceID, Name: "Alice"}) + + require.NoError(t, dao.Delete(ctx, bobID)) + + _, err = dao.Lookup(ctx, bobID) + require.ErrorIs(t, err, sql.ErrNoRows) + + require.NoError(t, dao.Update(ctx, &User{ID: charlieID, Name: "Chaplin"})) + + users, err := dao.List(ctx) + require.NoError(t, err) + + sort.Slice(users, func(i, j int) bool { + return users[i].Name < users[j].Name + }) + + require.Equal(t, users, []User{ + {ID: aliceID, Name: "Alice"}, + {ID: charlieID, Name: "Chaplin"}, + }) +} diff --git a/dao/model.go b/dao/model.go new file mode 100644 index 00000000..d2cebbe1 --- /dev/null +++ b/dao/model.go @@ -0,0 +1,22 @@ +package dao + +import ( + "context" +) + +type ( + UserID int + + User struct { + ID UserID + Name string + } + + Dao interface { + Create(ctx context.Context, u *User) (UserID, error) + Update(ctx context.Context, u *User) error + Delete(ctx context.Context, id UserID) error + Lookup(ctx context.Context, id UserID) (User, error) + List(ctx context.Context) ([]User, error) + } +) From 5f2b0f52fe0eb80c9c135c69f4e7e60f1362af04 Mon Sep 17 00:00:00 2001 From: Artem Garkavy Date: Sun, 13 Mar 2022 02:59:22 +0300 Subject: [PATCH 45/66] fix bug --- tparallel/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tparallel/README.md b/tparallel/README.md index f4a23c3b..3e0fcd46 100644 --- a/tparallel/README.md +++ b/tparallel/README.md @@ -5,7 +5,7 @@ Тест - это функция с сигнатурой `func(*T)`. Вам нужно реализовать функцию `Run(topTests []func(*T))`, запускающую множество top-level тестов. -Каждый тест получает аргументом уникальный объект `*T`, под объекту `T` на каждый запуск теста. +Каждый тест получает аргументом уникальный объект `*T`, по объекту `T` на каждый запуск теста. В начале все тесты выполняются последовательно. Если тест вызывает `t.Parallel()`, то он становится параллельным и блокируется на этом вызове. После этого, запускается следующий последовательный тест. From 1687b7bf8c80fe06657f5d6ee2262bf65d702ad5 Mon Sep 17 00:00:00 2001 From: Artem Garkavy Date: Sun, 27 Mar 2022 21:33:10 +0300 Subject: [PATCH 46/66] fix typos in lecture --- lectures/05-concurrency/lecture.slide | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/lectures/05-concurrency/lecture.slide b/lectures/05-concurrency/lecture.slide index 11a620cb..202dd457 100644 --- a/lectures/05-concurrency/lecture.slide +++ b/lectures/05-concurrency/lecture.slide @@ -17,7 +17,7 @@ Concurrency with Shared Memory a := 1 a += 1 -- Посылка значения из канал _happens_before_ получения этого значения из канала. +- Посылка значения из канала _happens_before_ получения этого значения из канала. - Два события A и B _происходят_одновременно_ (_are_concurrent_), если нельзя сказать что одно случилось раньше другого. @@ -312,18 +312,19 @@ Concurrency with Shared Memory func (once *Once) Do(f func()) { once.mu.Lock() defer once.mu.Unlock() - if done { + if once.done { return } - if running { + if once.running { once.cond.Wait() // releases and acquires mutex return } - running = true + + once.running = true once.mu.Unlock() f() once.mu.Lock() - done = true + once.done = true once.cond.Broadcast() } From e5710699ac86d01f4001635969f9a7e40a82a1e5 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 29 Mar 2022 02:55:30 +0300 Subject: [PATCH 47/66] [testequal] Simplify nil slice and map construction. --- testequal/assertions_test.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/testequal/assertions_test.go b/testequal/assertions_test.go index b2666ee5..0835e946 100644 --- a/testequal/assertions_test.go +++ b/testequal/assertions_test.go @@ -66,18 +66,18 @@ func TestNotEqual(t *testing.T) { {expected: []int{1, 2, 3}, actual: []int{1, 2, 3, 4}}, {expected: []int{1, 2, 3, 4}, actual: []int{1, 2, 3}}, {expected: []int{}, actual: []interface{}{}}, - {expected: []int{}, actual: *new([]int)}, + {expected: []int{}, actual: []int(nil)}, {expected: []int{}, actual: map[int]int{}}, {expected: map[string]string{"a": "b"}, actual: map[string]string{}}, {expected: map[string]string{"a": "b"}, actual: map[string]string{"a": "d"}}, {expected: map[string]string{"a": "b"}, actual: map[string]string{"a": "b", "c": "b"}}, {expected: map[string]string{"a": "b", "c": "b"}, actual: map[string]string{"a": "b"}}, {expected: map[string]string{"a": "b"}, actual: map[string]interface{}{"a": "b"}}, - {expected: map[string]string{}, actual: *new(map[string]string)}, + {expected: map[string]string{}, actual: map[string]string(nil)}, {expected: map[int]int{}, actual: []int{}}, - {expected: []byte{}, actual: *new([]byte)}, + {expected: []byte{}, actual: []byte(nil)}, {expected: []byte{}, actual: nil}, - {expected: *new([]byte), actual: nil}, + {expected: []byte(nil), actual: nil}, {expected: struct{}{}, actual: struct{}{}}, // unsupported type } { t.Run(fmt.Sprintf("%T_%T", tc.expected, tc.actual), func(t *testing.T) { From b509edc511bffd37dcc9ec0c01dbe3e7895eaa81 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 29 Mar 2022 16:37:23 +0300 Subject: [PATCH 48/66] Add CSV abbreviation to stylecheck. --- .golangci.yml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/.golangci.yml b/.golangci.yml index 207bcb7a..f91a73bf 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -43,6 +43,13 @@ linters-settings: stylecheck: # https://staticcheck.io/docs/options#checks checks: ["all", "-ST1018"] + # https://staticcheck.io/docs/options#initialisms + initialisms: [ + "ACL", "API", "ASCII", "CPU", "CSS", "DNS", "EOF", "GUID", "HTML", "HTTP", "HTTPS", "ID", "IP", "JSON", "QPS", + "RAM", "RPC", "SLA", "SMTP", "SQL", "SSH", "TCP", "TLS", "TTL", "UDP", "UI", "GID", "UID", "UUID", "URI", "URL", + "UTF8", "VM", "XML", "XMPP", "XSRF", "XSS", "CSV", + ] + linters: disable-all: true From a4e73a9831d27f81ea1b1f9ca6d09d6556929fed Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Tue, 29 Mar 2022 17:21:14 +0300 Subject: [PATCH 49/66] [dao] Fix typo. --- dao/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dao/README.md b/dao/README.md index 97258111..45196dae 100644 --- a/dao/README.md +++ b/dao/README.md @@ -7,4 +7,4 @@ - Метод `Update` меняет `Name` пользователя. - Метод `Delete` удаляет пользователя из таблицы. - Метод `Lookup` возвращает `Name` пользователя по `ID`. -- Метод `List` возвращает список все пользователей в таблице. +- Метод `List` возвращает список всех пользователей в таблице. From 72abaf8acdfe6b4b7478b28529106e6a3d3d5fe4 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 12:57:23 +0300 Subject: [PATCH 50/66] Fix --- dao/README.md | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/dao/README.md b/dao/README.md index 45196dae..314ee1a5 100644 --- a/dao/README.md +++ b/dao/README.md @@ -4,7 +4,21 @@ - Функция `CreateDao` должна создавать таблицу в базе данных. - Метод `Create` должен создавать нового пользователя и назначать его `ID`. + За генерацию `ID` должна отвечать база данных, использовать `rand` запрещается. - Метод `Update` меняет `Name` пользователя. - Метод `Delete` удаляет пользователя из таблицы. - Метод `Lookup` возвращает `Name` пользователя по `ID`. - Метод `List` возвращает список всех пользователей в таблице. + +## Запуск тестов на linux + +Для работы тестов на ubuntu нужно установить пакет `postgresql`. + +``` +sudo apt install postgresql +``` + +Если вы работаете на другом дистрибутиве linux, воспользуйтесь своим пакетным менеджером. Для работы тестов нужны исполняемые файлы `postgres` и `initdb`. + +Тесты сами запускают базу данных в начале, и останавливают её в конце. +База данных работает от текущего пользователя во временной директории. From d65fd9bcf17c84065bd7c188ef086ab9fdca1dde Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 14:19:47 +0300 Subject: [PATCH 51/66] Add ledger task --- ledger/README.md | 19 ++++++ ledger/ledger.go | 9 +++ ledger/ledger_test.go | 135 ++++++++++++++++++++++++++++++++++++++++++ ledger/model.go | 21 +++++++ 4 files changed, 184 insertions(+) create mode 100644 ledger/README.md create mode 100644 ledger/ledger.go create mode 100644 ledger/ledger_test.go create mode 100644 ledger/model.go diff --git a/ledger/README.md b/ledger/README.md new file mode 100644 index 00000000..eefe504d --- /dev/null +++ b/ledger/README.md @@ -0,0 +1,19 @@ +# ledger + +Реализуйте объект для хранения банковских счетов. Требуемый интерфейс находится в `model.go`. + +- Функция `New` должна создавать таблицу в базе данных. +- Метод `CreateAccount` должен создавать новый счёт с заданным `id`. +- Метод `GetBalance` должен возвращать текущий баланс. +- Метод `Deposit` должен зачислять деньги на счёт. +- Метод `Withdraw` должен снимать деньги со счёта. + Если на счету не достаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. +- Метод `Transfer` должен переводить деньги со счёта `from` на счёт `to`. + Если на счету `from` не достаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. + +Все операции должны быть атомарными. Для реализации некоторых методов +вам потребуется использовать транзакции и row-level локи. Ваша реализация не должна создавать дедлоки на уровне базы данных. + +Мы рекомендуем использовать функциональность `SELECT FOR UPDATE`. + +Комментарии по запуску postgres смотрите в задаче `dao`. \ No newline at end of file diff --git a/ledger/ledger.go b/ledger/ledger.go new file mode 100644 index 00000000..a82b6d15 --- /dev/null +++ b/ledger/ledger.go @@ -0,0 +1,9 @@ +//go:build !solution + +package ledger + +import "context" + +func New(ctx context.Context, dsn string) (Ledger, error) { + panic("not implemented") +} diff --git a/ledger/ledger_test.go b/ledger/ledger_test.go new file mode 100644 index 00000000..feed4db7 --- /dev/null +++ b/ledger/ledger_test.go @@ -0,0 +1,135 @@ +package ledger_test + +import ( + "context" + "errors" + "fmt" + "sync" + "testing" + "time" + + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/ledger" + "gitlab.com/slon/shad-go/pgfixture" +) + +func TestLedger(t *testing.T) { + dsn := pgfixture.Start(t) + + ctx := context.Background() + + l0, err := ledger.New(ctx, dsn) + require.NoError(t, err) + + t.Run("SimpleCommands", func(t *testing.T) { + checkBalance := func(account ledger.ID, amount ledger.Money) { + b, err := l0.GetBalance(ctx, account) + require.NoError(t, err) + require.Equal(t, b, amount) + } + + require.NoError(t, l0.CreateAccount(ctx, "a0")) + checkBalance("a0", 0) + + require.Error(t, l0.CreateAccount(ctx, "a0")) + + require.NoError(t, l0.Deposit(ctx, "a0", ledger.Money(100))) + checkBalance("a0", 100) + + require.NoError(t, l0.Withdraw(ctx, "a0", ledger.Money(50))) + checkBalance("a0", 50) + + require.ErrorIs(t, l0.Withdraw(ctx, "a0", ledger.Money(100)), ledger.ErrNoMoney) + + require.NoError(t, l0.CreateAccount(ctx, "a1")) + + require.NoError(t, l0.Transfer(ctx, "a0", "a1", ledger.Money(40))) + checkBalance("a0", 10) + checkBalance("a1", 40) + + require.ErrorIs(t, l0.Transfer(ctx, "a0", "a1", ledger.Money(50)), ledger.ErrNoMoney) + }) + + t.Run("Transactions", func(t *testing.T) { + const nAccounts = 10 + const initialBalance = 5 + + var accounts []ledger.ID + for i := 0; i < nAccounts; i++ { + id := ledger.ID(fmt.Sprint(i)) + accounts = append(accounts, id) + + require.NoError(t, l0.CreateAccount(ctx, id)) + require.NoError(t, l0.Deposit(ctx, id, initialBalance)) + } + + var wg sync.WaitGroup + done := make(chan struct{}) + + spawn := func(action func() error) { + wg.Add(1) + + go func() { + defer wg.Done() + + for { + select { + case <-done: + return + + default: + if err := action(); err != nil { + if !errors.Is(err, ledger.ErrNoMoney) { + t.Errorf("operation failed: %v", err) + return + } + } + } + } + }() + } + + for i := 0; i < nAccounts; i++ { + i := i + + account := accounts[i] + next := accounts[(i+1)%len(accounts)] + prev := accounts[(i+len(accounts)-1)%len(accounts)] + + spawn(func() error { + balance, err := l0.GetBalance(ctx, account) + if err != nil { + return err + } + + if balance < 0 { + return fmt.Errorf("%q balance is negative", account) + } + + return nil + }) + + spawn(func() error { + return l0.Transfer(ctx, account, next, 1) + }) + + spawn(func() error { + return l0.Transfer(ctx, account, prev, 1) + }) + } + + time.Sleep(time.Second * 10) + close(done) + wg.Wait() + + var total ledger.Money + for i := 0; i < nAccounts; i++ { + amount, err := l0.GetBalance(ctx, accounts[i]) + require.NoError(t, err) + + total += amount + } + + require.Equal(t, total, ledger.Money(initialBalance*nAccounts)) + }) +} diff --git a/ledger/model.go b/ledger/model.go new file mode 100644 index 00000000..3bafcc07 --- /dev/null +++ b/ledger/model.go @@ -0,0 +1,21 @@ +package ledger + +import ( + "context" + "errors" +) + +type ( + ID string + Money int64 +) + +var ErrNoMoney = errors.New("no money") + +type Ledger interface { + CreateAccount(ctx context.Context, id ID) error + GetBalance(ctx context.Context, id ID) (Money, error) + Deposit(ctx context.Context, id ID, amount Money) error + Withdraw(ctx context.Context, id ID, amount Money) error + Transfer(ctx context.Context, from, to ID, amount Money) error +} From f51848efa46ee7dc0f1b2c4343bf7d8040c060c2 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 16:21:18 +0300 Subject: [PATCH 52/66] Add shopfront task --- build.docker | 2 +- shopfront/README.md | 21 ++++++++++++ shopfront/model.go | 19 +++++++++++ shopfront/redis_test.go | 56 +++++++++++++++++++++++++++++++ shopfront/shopfront.go | 9 +++++ shopfront/shopfront_test.go | 66 +++++++++++++++++++++++++++++++++++++ 6 files changed, 172 insertions(+), 1 deletion(-) create mode 100644 shopfront/README.md create mode 100644 shopfront/model.go create mode 100644 shopfront/redis_test.go create mode 100644 shopfront/shopfront.go create mode 100644 shopfront/shopfront_test.go diff --git a/build.docker b/build.docker index 5dc4cec1..1b65e255 100644 --- a/build.docker +++ b/build.docker @@ -1,7 +1,7 @@ FROM golang:1.17 RUN apt-get update && apt-get install -y \ - rsync libssl-dev postgresql sudo \ + rsync libssl-dev postgresql sudo redis-server \ && rm -rf /var/lib/apt/lists/* RUN curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v1.44.0 diff --git a/shopfront/README.md b/shopfront/README.md new file mode 100644 index 00000000..18959b55 --- /dev/null +++ b/shopfront/README.md @@ -0,0 +1,21 @@ +# shopfront + +В этой задаче вам нужно реализовать хранилище счётчиков посещений поверх redis. + +- Метод `RecordView` запоминает, что пользователь посетил страницу `item`-а. +- Метод `GetItems` загружает счётчики для пачки `item` ов. В поле `item[i].Viewed` должен + быть записан флаг, означающий что пользователь посетил `i`-ый `item`. + +В этой задаче есть benchmark-и. Чтобы пройти его, ваше решение должно использовать [pipelining](https://redis.io/docs/manual/pipelining/). + +## Запуск тестов на linux + +Для работы тестов на ubuntu нужно установить пакет `redis-server`. + +``` +sudo apt install redis-server +``` + +Если вы работаете на другом дистрибутиве linux, воспользуйтесь своим пакетным менеджером. + +Тесты сами запускают `redis` в начале, и останавливают его в конце. diff --git a/shopfront/model.go b/shopfront/model.go new file mode 100644 index 00000000..0f129d20 --- /dev/null +++ b/shopfront/model.go @@ -0,0 +1,19 @@ +package shopfront + +import "context" + +type ( + ItemID int64 + UserID int64 +) + +type Item struct { + ViewCount int + Viewed bool +} + +type Counters interface { + GetItems(ctx context.Context, ids []ItemID, userID UserID) ([]Item, error) + + RecordView(ctx context.Context, id ItemID, userID UserID) error +} diff --git a/shopfront/redis_test.go b/shopfront/redis_test.go new file mode 100644 index 00000000..20aecfd4 --- /dev/null +++ b/shopfront/redis_test.go @@ -0,0 +1,56 @@ +package shopfront_test + +import ( + "os" + "os/exec" + "time" + + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/tools/testtool" +) + +type testingTB interface { + Logf(format string, args ...interface{}) + Fatalf(format string, args ...interface{}) + Errorf(format string, args ...interface{}) + FailNow() + Cleanup(func()) +} + +func StartRedis(tb testingTB) string { + if redis, ok := os.LookupEnv("REDIS"); ok { + tb.Logf("using external redis server; REDIS=%s", redis) + return redis + } + + port, err := testtool.GetFreePort() + require.NoError(tb, err) + + _, err = exec.LookPath("redis-server") + if err != nil { + tb.Fatalf("redis-server binary is not found; is redis installed?") + } + + cmd := exec.Command("redis-server", "--port", port, "--save", "", "--appendonly", "no") + cmd.Stderr = os.Stderr + + require.NoError(tb, cmd.Start()) + + finished := make(chan error, 1) + go func() { + finished <- cmd.Wait() + }() + + select { + case err := <-finished: + tb.Fatalf("redis server terminated: %v", err) + + case <-time.After(time.Second / 2): + } + + tb.Cleanup(func() { + _ = cmd.Process.Kill() + }) + + return "localhost:" + port +} diff --git a/shopfront/shopfront.go b/shopfront/shopfront.go new file mode 100644 index 00000000..60b038fc --- /dev/null +++ b/shopfront/shopfront.go @@ -0,0 +1,9 @@ +//go:build !solution + +package shopfront + +import "github.com/go-redis/redis/v8" + +func New(rdb *redis.Client) Counters { + panic("not implemented") +} diff --git a/shopfront/shopfront_test.go b/shopfront/shopfront_test.go new file mode 100644 index 00000000..c94b991d --- /dev/null +++ b/shopfront/shopfront_test.go @@ -0,0 +1,66 @@ +package shopfront_test + +import ( + "context" + "testing" + + "github.com/go-redis/redis/v8" + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/shopfront" +) + +func TestShopfront(t *testing.T) { + rdb := redis.NewClient(&redis.Options{ + Addr: StartRedis(t), + }) + + ctx := context.Background() + + c := shopfront.New(rdb) + + items, err := c.GetItems(ctx, []shopfront.ItemID{1, 2, 3, 4}, 42) + require.NoError(t, err) + require.Equal(t, items, []shopfront.Item{ + {}, + {}, + {}, + {}, + }) + + require.NoError(t, c.RecordView(ctx, 3, 42)) + require.NoError(t, c.RecordView(ctx, 2, 42)) + + require.NoError(t, c.RecordView(ctx, 2, 4242)) + + items, err = c.GetItems(ctx, []shopfront.ItemID{1, 2, 3, 4}, 42) + require.NoError(t, err) + require.Equal(t, items, []shopfront.Item{ + {}, + {ViewCount: 2, Viewed: true}, + {ViewCount: 1, Viewed: true}, + {}, + }) +} + +func BenchmarkShopfront(b *testing.B) { + const nItems = 1024 + + rdb := redis.NewClient(&redis.Options{ + Addr: StartRedis(b), + }) + + ctx := context.Background() + c := shopfront.New(rdb) + + var ids []shopfront.ItemID + for i := 0; i < nItems; i++ { + ids = append(ids, shopfront.ItemID(i)) + require.NoError(b, c.RecordView(ctx, shopfront.ItemID(i), 42)) + } + + b.ResetTimer() + for i := 0; i < b.N; i++ { + _, err := c.GetItems(ctx, ids, 42) + require.NoError(b, err) + } +} From 28b48aada9d891406464b11bbd05e4a1dc992688 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 16:30:47 +0300 Subject: [PATCH 53/66] Fix flaky test --- pgfixture/pg.go | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/pgfixture/pg.go b/pgfixture/pg.go index 8b2d3a28..39485399 100644 --- a/pgfixture/pg.go +++ b/pgfixture/pg.go @@ -8,6 +8,9 @@ import ( "path/filepath" "testing" "time" + + "github.com/stretchr/testify/require" + "gitlab.com/slon/shad-go/tools/testtool" ) func lookPath(t *testing.T, name string) string { @@ -50,9 +53,12 @@ func Start(t *testing.T) string { t.Fatalf("initdb failed: %v", err) } + port, err := testtool.GetFreePort() + require.NoError(t, err) + pgrun := t.TempDir() - cmd = exec.Command(lookPath(t, "postgres"), "-D", pgdata, "-k", pgrun, "-F") + cmd = exec.Command(lookPath(t, "postgres"), "-D", pgdata, "-k", pgrun, "-F", "-p", port) cmd.Stderr = os.Stderr cmd.Stdout = os.Stdout if err := cmd.Start(); err != nil { @@ -75,5 +81,5 @@ func Start(t *testing.T) string { _ = cmd.Process.Kill() }) - return fmt.Sprintf("host=%s database=postgres", pgrun) + return fmt.Sprintf("host=localhost port=%s database=postgres", port) } From 55863b75ba9e60484cf904649abb8a9ae558866f Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:40:40 +0300 Subject: [PATCH 54/66] Add instructions to run databases in docker. --- dao/README.md | 22 ++++++++++++++++++++++ dao/docker-compose.yaml | 10 ++++++++++ dockertest/README.md | 2 -- ledger/README.md | 2 +- ledger/docker-compose.yaml | 10 ++++++++++ shopfront/README.md | 8 ++++++++ 6 files changed, 51 insertions(+), 3 deletions(-) create mode 100644 dao/docker-compose.yaml create mode 100644 ledger/docker-compose.yaml diff --git a/dao/README.md b/dao/README.md index 314ee1a5..63b7e720 100644 --- a/dao/README.md +++ b/dao/README.md @@ -22,3 +22,25 @@ sudo apt install postgresql Тесты сами запускают базу данных в начале, и останавливают её в конце. База данных работает от текущего пользователя во временной директории. + +## Запуск postgres в docker + +Даже если у вас linux (и уж тем более, если нет), вы можете не захотеть ставить postgres в систему. +Альтернативный способ — запустить бд в докере. + +Для этого нужно установить docker и docker-compose по инструкции из [dockertest](../dockertest/README.md). +Добвиться успешного запуска +``` +go test -v ./dockertest/... +``` + +Запускать тесты можно будет так: +``` +(cd dao && docker-compose up -d && sleep 1 && env PGCONN="host=127.0.0.1 port=5432 database=shad-go user=gopher password=pass" go test -v ./... -count=1 || true && docker-compose down) +``` +Эта команда стартует docker с postgresql, запускает тесты, передав им DSN через переменную окружения, удаляет контейнеры в конце. + +Как подчистить контейнеры, если что-то пошло не так: +``` +(cd dao && docker-compose down) +``` diff --git a/dao/docker-compose.yaml b/dao/docker-compose.yaml new file mode 100644 index 00000000..0bc47820 --- /dev/null +++ b/dao/docker-compose.yaml @@ -0,0 +1,10 @@ +version: '3' +services: + pg: + image: postgres:latest + environment: + POSTGRES_DB: shad-go + POSTGRES_USER: gopher + POSTGRES_PASSWORD: pass + ports: + - 5432:5432 diff --git a/dockertest/README.md b/dockertest/README.md index 7232814a..2dc6fe09 100644 --- a/dockertest/README.md +++ b/dockertest/README.md @@ -9,8 +9,6 @@ go test -v ./dockertest/... -count=1 ``` -Только **после того, как тесты пройдут локально,** можете запушить решение в систему. - ### С чего начать?
diff --git a/ledger/README.md b/ledger/README.md index eefe504d..c1b3db16 100644 --- a/ledger/README.md +++ b/ledger/README.md @@ -16,4 +16,4 @@ Мы рекомендуем использовать функциональность `SELECT FOR UPDATE`. -Комментарии по запуску postgres смотрите в задаче `dao`. \ No newline at end of file +Комментарии по запуску postgres смотрите в задаче [dao](../dao/). diff --git a/ledger/docker-compose.yaml b/ledger/docker-compose.yaml new file mode 100644 index 00000000..0bc47820 --- /dev/null +++ b/ledger/docker-compose.yaml @@ -0,0 +1,10 @@ +version: '3' +services: + pg: + image: postgres:latest + environment: + POSTGRES_DB: shad-go + POSTGRES_USER: gopher + POSTGRES_PASSWORD: pass + ports: + - 5432:5432 diff --git a/shopfront/README.md b/shopfront/README.md index 18959b55..18c59255 100644 --- a/shopfront/README.md +++ b/shopfront/README.md @@ -19,3 +19,11 @@ sudo apt install redis-server Если вы работаете на другом дистрибутиве linux, воспользуйтесь своим пакетным менеджером. Тесты сами запускают `redis` в начале, и останавливают его в конце. + +## Запуск redis в docker + +Комментарии по запуску бд в docker смотрите в задаче [dao](../dao/). + +``` +(cd shopfront && docker-compose up -d && sleep 1 && env REDIS="localhost:6379" go test -v ./... -count=1 || true && docker-compose down) +``` From 2d58ba80dbfc5f252e1475a7f38ce2afab4ae233 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:41:16 +0300 Subject: [PATCH 55/66] [ledger] Fix readme. --- ledger/README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ledger/README.md b/ledger/README.md index c1b3db16..bf402b86 100644 --- a/ledger/README.md +++ b/ledger/README.md @@ -7,9 +7,9 @@ - Метод `GetBalance` должен возвращать текущий баланс. - Метод `Deposit` должен зачислять деньги на счёт. - Метод `Withdraw` должен снимать деньги со счёта. - Если на счету не достаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. + Если на счету недостаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. - Метод `Transfer` должен переводить деньги со счёта `from` на счёт `to`. - Если на счету `from` не достаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. + Если на счету `from` недостаточно денег, метод должен возвращать ошибку `ledger.ErrNoMoney`. Все операции должны быть атомарными. Для реализации некоторых методов вам потребуется использовать транзакции и row-level локи. Ваша реализация не должна создавать дедлоки на уровне базы данных. From 1053c1a5669f0726a2e22c68344ee9c4aea8b389 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:41:44 +0300 Subject: [PATCH 56/66] [ledger] Fix argument order in require.Equal. --- ledger/ledger_test.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ledger/ledger_test.go b/ledger/ledger_test.go index feed4db7..cfc909fb 100644 --- a/ledger/ledger_test.go +++ b/ledger/ledger_test.go @@ -25,7 +25,7 @@ func TestLedger(t *testing.T) { checkBalance := func(account ledger.ID, amount ledger.Money) { b, err := l0.GetBalance(ctx, account) require.NoError(t, err) - require.Equal(t, b, amount) + require.Equal(t, amount, b) } require.NoError(t, l0.CreateAccount(ctx, "a0")) @@ -130,6 +130,6 @@ func TestLedger(t *testing.T) { total += amount } - require.Equal(t, total, ledger.Money(initialBalance*nAccounts)) + require.Equal(t, ledger.Money(initialBalance*nAccounts), total) }) } From f52fb5f7183456001e8550b12181c83a30567269 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:51:01 +0300 Subject: [PATCH 57/66] [shopfront] Add docker-compose.yaml. --- shopfront/docker-compose.yaml | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 shopfront/docker-compose.yaml diff --git a/shopfront/docker-compose.yaml b/shopfront/docker-compose.yaml new file mode 100644 index 00000000..d761b3fe --- /dev/null +++ b/shopfront/docker-compose.yaml @@ -0,0 +1,7 @@ +version: '3' +services: + redis: + image: "redis:alpine" + hostname: redis + ports: + - "6379:6379" From 669c0733d2938ca6e068e193257f9dcc631f4fc5 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:54:14 +0300 Subject: [PATCH 58/66] [dao, shopfront] Fix readme. --- dao/README.md | 2 +- shopfront/README.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dao/README.md b/dao/README.md index 63b7e720..51eeea65 100644 --- a/dao/README.md +++ b/dao/README.md @@ -29,7 +29,7 @@ sudo apt install postgresql Альтернативный способ — запустить бд в докере. Для этого нужно установить docker и docker-compose по инструкции из [dockertest](../dockertest/README.md). -Добвиться успешного запуска +Добиться успешного запуска ``` go test -v ./dockertest/... ``` diff --git a/shopfront/README.md b/shopfront/README.md index 18c59255..fa7b4c43 100644 --- a/shopfront/README.md +++ b/shopfront/README.md @@ -4,7 +4,7 @@ - Метод `RecordView` запоминает, что пользователь посетил страницу `item`-а. - Метод `GetItems` загружает счётчики для пачки `item` ов. В поле `item[i].Viewed` должен - быть записан флаг, означающий что пользователь посетил `i`-ый `item`. + быть записан флаг, означающий, что пользователь посетил `i`-ый `item`. В этой задаче есть benchmark-и. Чтобы пройти его, ваше решение должно использовать [pipelining](https://redis.io/docs/manual/pipelining/). From 231fdc1201d61d39983a2d19b95df34b14d7c169 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 17:59:14 +0300 Subject: [PATCH 59/66] Release sql. --- .deadlines.yml | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/.deadlines.yml b/.deadlines.yml index 26539e0f..89f861ee 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -1,3 +1,16 @@ +- group: SQL + start: 31-03-2022 18:00 + deadline: 17-04-2022 23:59 + tasks: + - task: wscat + score: 100 + - task: dao + score: 100 + - task: ledger + score: 100 + - task: shopfront + score: 100 + - group: HTTP start: 23-03-2022 18:00 deadline: 10-04-2022 23:59 From fb13bf5eb597dd913a4091c434b26752be4fe580 Mon Sep 17 00:00:00 2001 From: Arseny Balobanov Date: Thu, 31 Mar 2022 18:25:39 +0300 Subject: [PATCH 60/66] [wscat] Try increasing timeout. --- wscat/main_test.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/wscat/main_test.go b/wscat/main_test.go index cf15c203..cfed8742 100644 --- a/wscat/main_test.go +++ b/wscat/main_test.go @@ -76,7 +76,7 @@ func startCommand(t *testing.T, addr string) (conn *Conn, stop func()) { // try killing softly _ = cmd.Process.Signal(syscall.SIGTERM) - ctx, cancel := context.WithTimeout(context.Background(), time.Millisecond*100) + ctx, cancel := context.WithTimeout(context.Background(), time.Millisecond*200) defer cancel() select { @@ -132,7 +132,7 @@ func TestWScat(t *testing.T) { } // give client time to make a request - time.Sleep(time.Millisecond * 100) + time.Sleep(time.Millisecond * 200) stop() require.Equal(t, bytes.Join(in, nil), bytes.Join(received, nil)) From 391cd002d85d3d0f88a3de775e89fc3dc6347508 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 15:59:32 +0000 Subject: [PATCH 61/66] Update lectures/07-sql/nulls/rows.go --- lectures/07-sql/nulls/rows.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lectures/07-sql/nulls/rows.go b/lectures/07-sql/nulls/rows.go index 75975572..e582a53f 100644 --- a/lectures/07-sql/nulls/rows.go +++ b/lectures/07-sql/nulls/rows.go @@ -7,7 +7,7 @@ import ( ) func Results(ctx context.Context, db *sql.DB) { - rows, err := db.QueryContext(ctx, "SELECT id, name FROM users WHERE id = $1", 1) + rows, err := db.QueryContext(ctx, "SELECT name FROM users WHERE id = $1", 1) if err != nil { log.Fatal(err) } From ab121485bdf007d13e61ee3a7b7ce75c7d3196dc Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 19:10:53 +0300 Subject: [PATCH 62/66] Add note about RETURNING --- dao/README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/dao/README.md b/dao/README.md index 51eeea65..a9a43cff 100644 --- a/dao/README.md +++ b/dao/README.md @@ -5,6 +5,7 @@ - Функция `CreateDao` должна создавать таблицу в базе данных. - Метод `Create` должен создавать нового пользователя и назначать его `ID`. За генерацию `ID` должна отвечать база данных, использовать `rand` запрещается. + `pgx` не поддерживает `LastInsertId`, используйте синтаксис `RETURNING id`. - Метод `Update` меняет `Name` пользователя. - Метод `Delete` удаляет пользователя из таблицы. - Метод `Lookup` возвращает `Name` пользователя по `ID`. From 8ae368ec09f964c772ce6b5d473ae0269fa26240 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 20:23:32 +0300 Subject: [PATCH 63/66] Try fixing pg --- tools/testtool/commands/test_submission.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tools/testtool/commands/test_submission.go b/tools/testtool/commands/test_submission.go index eb7a7349..26a27bbc 100644 --- a/tools/testtool/commands/test_submission.go +++ b/tools/testtool/commands/test_submission.go @@ -423,7 +423,7 @@ func noMoreThanTwoTimesWorse(old, new *benchstat.Metrics) (float64, error) { func compareToBaseline(testPkg, privateRepo string, run []byte) error { var buf bytes.Buffer - goTest := exec.Command("go", "test", "-tags", "private,solution", "-bench=.", testPkg) + goTest := exec.Command("go", "test", "-tags", "private,solution", "-bench=.", "-run=^$", testPkg) goTest.Dir = privateRepo goTest.Stdout = &buf goTest.Stderr = os.Stderr From 6410bedced37b984ab07a5d31930610c3924562c Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Thu, 31 Mar 2022 19:44:08 +0000 Subject: [PATCH 64/66] Update .deadlines.yml --- .deadlines.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.deadlines.yml b/.deadlines.yml index 89f861ee..8cef5691 100644 --- a/.deadlines.yml +++ b/.deadlines.yml @@ -3,11 +3,11 @@ deadline: 17-04-2022 23:59 tasks: - task: wscat - score: 100 + score: 200 - task: dao score: 100 - task: ledger - score: 100 + score: 200 - task: shopfront score: 100 From 2f96b796abd938bc9c5858f0440c55e19403450b Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 2 Apr 2022 10:57:00 +0000 Subject: [PATCH 65/66] Update dupcall/README.md --- dupcall/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dupcall/README.md b/dupcall/README.md index b1ee6617..32a6cff2 100644 --- a/dupcall/README.md +++ b/dupcall/README.md @@ -1,6 +1,6 @@ # dupcall -В этом задании нужно реализовать свою вариацию на тему singleflight. +В этом задании нужно реализовать свою вариацию на тему singleflight. Использовать в реализации singleflight нельзя. Объект `dupcall.Call` должен дедуплицировать вызовы дорогой функции, правильно обрабатывая отмену контекста. From d242514137f179f161df2e3d1c518f12efb28e81 Mon Sep 17 00:00:00 2001 From: Fedor Korotkiy Date: Sat, 2 Apr 2022 14:34:35 +0300 Subject: [PATCH 66/66] Upgrade golangci-lint --- build.docker | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.docker b/build.docker index 24a4cf5c..5c74c8bd 100644 --- a/build.docker +++ b/build.docker @@ -4,7 +4,7 @@ RUN apt-get update && apt-get install -y \ rsync libssl-dev \ && rm -rf /var/lib/apt/lists/* -RUN curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v1.44.0 +RUN curl -sSfL https://raw.githubusercontent.com/golangci/golangci-lint/master/install.sh | sh -s -- -b $(go env GOPATH)/bin v1.45.2 RUN curl -L "https://github.com/docker/compose/releases/download/1.28.5/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose RUN chmod +x /usr/local/bin/docker-compose RUN curl -fsSL https://get.docker.com | sh