From 694c64f21716d33a912587143f7e1e43eeed2ef0 Mon Sep 17 00:00:00 2001
From: Rui Lopes <76881129+RuiL1904@users.noreply.github.com>
Date: Sat, 19 Aug 2023 15:57:11 +0100
Subject: [PATCH 1/4] chore: add license (#328)
---
LICENSE.txt | 22 ++++++++++++++++++++++
1 file changed, 22 insertions(+)
create mode 100644 LICENSE.txt
diff --git a/LICENSE.txt b/LICENSE.txt
new file mode 100644
index 000000000..3e3d7de59
--- /dev/null
+++ b/LICENSE.txt
@@ -0,0 +1,22 @@
+MIT License
+
+Copyright (c) 2023 CeSIUM - Centro de Estudantes de Eng. Informática
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+SOFTWARE.
+
From 35dbb051fd7ba5d9829064a7516463b6332da3f5 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jo=C3=A3o=20Lobo?=
<30907944+joaodiaslobo@users.noreply.github.com>
Date: Sat, 19 Aug 2023 17:57:19 +0100
Subject: [PATCH 2/4] feat: add user profile (#321)
* Add handle field to users
* Add user profile page route
* Add unique constraint to handle column
* Profile page
* Follow suggestion regarding user table constraints
* Fix tests and run formatter
* Fix and add tests, change handle requirements
* Implement suggestions
* Add unit tests
* Add user settings button to profile page
* Run formatter
* Update edit button
---
lib/atomic/accounts.ex | 29 +++++++++
lib/atomic/accounts/user.ex | 33 +++++++++-
.../live/membership_live/index.html.heex | 6 +-
lib/atomic_web/live/user_live/show.ex | 36 +++++++++++
lib/atomic_web/live/user_live/show.html.heex | 62 +++++++++++++++++++
lib/atomic_web/router.ex | 2 +
.../templates/layout/live.html.heex | 11 ++--
.../templates/user_registration/new.html.heex | 8 +++
...0221014155230_create_users_auth_tables.exs | 2 +
priv/repo/seeds/accounts.exs | 2 +
test/atomic/accounts_test.exs | 39 ++++++++++--
test/support/factories/accounts_factory.ex | 1 +
12 files changed, 219 insertions(+), 12 deletions(-)
create mode 100644 lib/atomic_web/live/user_live/show.ex
create mode 100644 lib/atomic_web/live/user_live/show.html.heex
diff --git a/lib/atomic/accounts.ex b/lib/atomic/accounts.ex
index 5679bbf1d..e33ddb211 100644
--- a/lib/atomic/accounts.ex
+++ b/lib/atomic/accounts.ex
@@ -26,6 +26,22 @@ defmodule Atomic.Accounts do
Repo.get_by(User, email: email)
end
+ @doc """
+ Gets a user by handle.
+
+ ## Examples
+
+ iex> get_user_by_handle("foo_bar")
+ %User{}
+
+ iex> get_user_by_handle("unknown")
+ nil
+
+ """
+ def get_user_by_handle(handle) when is_binary(handle) do
+ Repo.get_by(User, handle: handle)
+ end
+
@doc """
Gets a user by email and password.
@@ -197,6 +213,19 @@ defmodule Atomic.Accounts do
User.email_changeset(user, attrs)
end
+ @doc """
+ Returns an `%Ecto.Changeset{}` for changing the user handle.
+
+ ## Examples
+
+ iex> change_user_handle(user)
+ %Ecto.Changeset{data: %User{}}
+
+ """
+ def change_user_handle(user, attrs \\ %{}) do
+ User.handle_changeset(user, attrs)
+ end
+
@doc """
Emulates that the email will change without actually changing
it in the database.
diff --git a/lib/atomic/accounts/user.ex b/lib/atomic/accounts/user.ex
index a2ec48297..577d6c9b9 100644
--- a/lib/atomic/accounts/user.ex
+++ b/lib/atomic/accounts/user.ex
@@ -9,7 +9,7 @@ defmodule Atomic.Accounts.User do
alias Atomic.Organizations.{Membership, Organization}
alias Atomic.Uploaders.ProfilePicture
- @required_fields ~w(email password)a
+ @required_fields ~w(email handle password)a
@optional_fields ~w(name role confirmed_at course_id default_organization_id)a
@roles ~w(admin student)a
@@ -17,6 +17,7 @@ defmodule Atomic.Accounts.User do
schema "users" do
field :name, :string
field :email, :string
+ field :handle, :string
field :password, :string, virtual: true, redact: true
field :hashed_password, :string, redact: true
field :confirmed_at, :naive_datetime
@@ -53,6 +54,7 @@ defmodule Atomic.Accounts.User do
user
|> cast(attrs, @required_fields ++ @optional_fields)
|> validate_email()
+ |> validate_handle()
|> validate_password(opts)
end
@@ -79,6 +81,20 @@ defmodule Atomic.Accounts.User do
|> unique_constraint(:email)
end
+ defp validate_handle(changeset) do
+ changeset
+ |> validate_required([:handle])
+ |> validate_format(:handle, ~r/^[a-zA-Z0-9_.]+$/,
+ message:
+ Gettext.gettext(
+ "must only contain alphanumeric characters, numbers, underscores and periods"
+ )
+ )
+ |> validate_length(:handle, min: 3, max: 30)
+ |> unsafe_validate_unique(:handle, Atomic.Repo)
+ |> unique_constraint(:handle)
+ end
+
defp validate_password(changeset, opts) do
changeset
|> validate_required([:password])
@@ -119,6 +135,21 @@ defmodule Atomic.Accounts.User do
end
end
+ @doc """
+ A user changeset for changing the handle.
+
+ It requires the handle to change otherwise an error is added.
+ """
+ def handle_changeset(user, attrs) do
+ user
+ |> cast(attrs, [:handle])
+ |> validate_handle()
+ |> case do
+ %{changes: %{handle: _}} = changeset -> changeset
+ %{} = changeset -> add_error(changeset, :handle, "did not change")
+ end
+ end
+
@doc """
A user changeset for changing the password.
diff --git a/lib/atomic_web/live/membership_live/index.html.heex b/lib/atomic_web/live/membership_live/index.html.heex
index 96955f2a1..e5c3b1785 100644
--- a/lib/atomic_web/live/membership_live/index.html.heex
+++ b/lib/atomic_web/live/membership_live/index.html.heex
@@ -30,7 +30,11 @@
<%= for membership <- @memberships do %>
<%= membership.number %>
-
<%= membership.user.name %>
+
+ <%= live_redirect to: Routes.user_show_path(@socket, :show, membership.user.handle) do %>
+ <%= membership.user.name %>
+ <% end %>
+
+ <%= for {organization, index} <- Enum.with_index(@organizations) do %>
+ <%= live_redirect to: Routes.organization_show_path(@socket, :show, organization) do %>
+
+
+ <%= if organization.logo do %>
+
+
+
+ <% else %>
+
+
+ <%= Atomic.Accounts.extract_initials(organization.name) %>
+
+
+ <% end %>
+
+ <%= live_patch to: Routes.user_settings_path(@socket, :edit), class: "inline-flex px-6 py-2 text-sm font-medium text-orange-500 bg-white border-2 border-orange-500 rounded-md shadow-sm hover:bg-orange-500 hover:text-white" do %>
+ Edit
+ <% end %>
+
+ <% end %>
+
+
diff --git a/lib/atomic_web/router.ex b/lib/atomic_web/router.ex
index b9993ec15..7188c9cbf 100644
--- a/lib/atomic_web/router.ex
+++ b/lib/atomic_web/router.ex
@@ -36,6 +36,8 @@ defmodule AtomicWeb.Router do
live "/organizations", OrganizationLive.Index, :index
live "/organizations/:organization_id", OrganizationLive.Show, :show
+ live "/profile/:handle", UserLive.Show, :show
+
scope "/organizations/:organization_id" do
live "/board/", BoardLive.Index, :index
live "/board/:id", BoardLive.Show, :show
diff --git a/lib/atomic_web/templates/layout/live.html.heex b/lib/atomic_web/templates/layout/live.html.heex
index bf76b873d..630fec9d3 100644
--- a/lib/atomic_web/templates/layout/live.html.heex
+++ b/lib/atomic_web/templates/layout/live.html.heex
@@ -201,11 +201,14 @@
Calendar
<% end %>
- <%= live_redirect to: Routes.user_settings_path(@socket, :edit), class: "bg-zinc-200 flex items-center gap-x-4 px-6 py-3 text-sm font-semibold leading-6 text-gray-900" do %>
+ <%= live_redirect to: Routes.user_show_path(@socket, :show, @current_user.handle), class: "bg-zinc-200 flex items-center gap-x-4 px-6 py-3 text-sm font-semibold leading-6 text-gray-900" do %>
- <%= Atomic.Accounts.extract_initials(@current_user.email) %>
+ <%= Atomic.Accounts.extract_initials(@current_user.name) %>
+
+
+
<%= @current_user.name %>
+
@<%= @current_user.handle %>
- <%= @current_user.email %>
<% end %>
@@ -217,7 +220,7 @@
<%= if @current_organization do %>
- <%= live_redirect to: Routes.activity_index_path(@socket, :index, @current_organization), class: "text-zinc-400 hover:text-zinc-500" do %>
+ <%= live_redirect to: Routes.home_index_path(@socket, :index), class: "text-zinc-400 hover:text-zinc-500" do %>
diff --git a/lib/atomic_web/templates/user_registration/new.html.heex b/lib/atomic_web/templates/user_registration/new.html.heex
index 28e0ee17b..73c5c0923 100644
--- a/lib/atomic_web/templates/user_registration/new.html.heex
+++ b/lib/atomic_web/templates/user_registration/new.html.heex
@@ -17,6 +17,14 @@
) %>
<%= error_tag(f, :email) %>
+ <%= label(f, :handle, class: "sr-only") %>
+ <%= text_input(f, :handle,
+ required: true,
+ placeholder: gettext("Username"),
+ class: "mt-1 relative block lg:w-96 w-full appearance-none rounded border border-zinc-300 px-3 py-2 text-zinc-900 placeholder-zinc-500 focus:z-10 focus:border-indigo-400 focus:outline-none sm:text-sm"
+ ) %>
+ <%= error_tag(f, :handle) %>
+
<%= label(f, :password, class: "sr-only") %>
<%= password_input(f, :password,
required: true,
diff --git a/priv/repo/migrations/20221014155230_create_users_auth_tables.exs b/priv/repo/migrations/20221014155230_create_users_auth_tables.exs
index f7fc7f948..ec56d9826 100644
--- a/priv/repo/migrations/20221014155230_create_users_auth_tables.exs
+++ b/priv/repo/migrations/20221014155230_create_users_auth_tables.exs
@@ -8,6 +8,7 @@ defmodule Atomic.Repo.Migrations.CreateUsersAuthTables do
add :id, :binary_id, primary_key: true
add :name, :string
add :email, :citext, null: false
+ add :handle, :citext, null: false
add :hashed_password, :string, null: false
add :confirmed_at, :naive_datetime
add :profile_picture, :string
@@ -21,6 +22,7 @@ defmodule Atomic.Repo.Migrations.CreateUsersAuthTables do
end
create unique_index(:users, [:email])
+ create unique_index(:users, [:handle])
create table(:users_tokens, primary_key: false) do
add :id, :binary_id, primary_key: true
diff --git a/priv/repo/seeds/accounts.exs b/priv/repo/seeds/accounts.exs
index dd6c763db..7e06fd0db 100644
--- a/priv/repo/seeds/accounts.exs
+++ b/priv/repo/seeds/accounts.exs
@@ -111,10 +111,12 @@ defmodule Atomic.Repo.Seeds.Accounts do
for character <- characters do
email = (character |> String.downcase() |> String.replace(~r/\s*/, "")) <> "@mail.pt"
+ handle = character |> String.downcase() |> String.replace(~r/\s/, "_")
user = %{
"name" => character,
"email" => email,
+ "handle" => handle,
"password" => "password1234",
"role" => role,
"course_id" => Enum.random(courses).id,
diff --git a/test/atomic/accounts_test.exs b/test/atomic/accounts_test.exs
index 5ea1c2fe9..b662d1f79 100644
--- a/test/atomic/accounts_test.exs
+++ b/test/atomic/accounts_test.exs
@@ -53,19 +53,27 @@ defmodule Atomic.AccountsTest do
} = errors_on(changeset)
end
- test "validates email and password when given" do
- {:error, changeset} = Accounts.register_user(%{email: "not valid", password: "not valid"})
+ test "validates email, handle and password when given" do
+ {:error, changeset} =
+ Accounts.register_user(%{email: "not valid", handle: "not valid", password: "not valid"})
assert %{
email: ["must have the @ sign and no spaces"],
+ handle: [
+ "must only contain alphanumeric characters, numbers, underscores and periods"
+ ],
password: ["should be at least 12 character(s)"]
} = errors_on(changeset)
end
- test "validates maximum values for email and password for security" do
+ test "validates maximum values for email, handle and password for security" do
too_long = String.duplicate("db", 100)
- {:error, changeset} = Accounts.register_user(%{email: too_long, password: too_long})
+
+ {:error, changeset} =
+ Accounts.register_user(%{email: too_long, handle: too_long, password: too_long})
+
assert "should be at most 160 character(s)" in errors_on(changeset).email
+ assert "should be at most 30 character(s)" in errors_on(changeset).handle
assert "should be at most 72 character(s)" in errors_on(changeset).password
end
@@ -79,11 +87,22 @@ defmodule Atomic.AccountsTest do
assert "has already been taken" in errors_on(changeset).email
end
+ test "validates handle uniqueness" do
+ %{handle: handle} = insert(:user)
+ {:error, changeset} = Accounts.register_user(%{handle: handle})
+ assert "has already been taken" in errors_on(changeset).handle
+
+ # Now try with the upper cased handle too, to check that handle case is ignored.
+ {:error, changeset} = Accounts.register_user(%{handle: String.upcase(handle)})
+ assert "has already been taken" in errors_on(changeset).handle
+ end
+
test "registers users with a hashed password" do
user_attrs = params_for(:user) |> Map.put(:password, valid_user_password())
{:ok, user} = Accounts.register_user(user_attrs)
assert user.email == user_attrs.email
+ assert user.handle == user_attrs.handle
assert is_binary(user.hashed_password)
assert is_nil(user.confirmed_at)
assert is_nil(user.password)
@@ -93,17 +112,18 @@ defmodule Atomic.AccountsTest do
describe "change_user_registration/2" do
test "returns a changeset" do
assert %Ecto.Changeset{} = changeset = Accounts.change_user_registration(%User{})
- assert changeset.required == [:password, :email]
+ assert changeset.required == [:password, :handle, :email]
end
test "allows fields to be set" do
email = Faker.Internet.email()
password = valid_user_password()
+ handle = Faker.Internet.user_name()
changeset =
Accounts.change_user_registration(
%User{},
- params_for(:user, %{email: email, password: password})
+ params_for(:user, %{email: email, handle: handle, password: password})
)
assert changeset.valid?
@@ -120,6 +140,13 @@ defmodule Atomic.AccountsTest do
end
end
+ describe "change_user_handle/2" do
+ test "returns a user changeset" do
+ assert %Ecto.Changeset{} = changeset = Accounts.change_user_handle(%User{})
+ assert changeset.required == [:handle]
+ end
+ end
+
describe "apply_user_email/3" do
setup do
%{user: insert(:user)}
diff --git a/test/support/factories/accounts_factory.ex b/test/support/factories/accounts_factory.ex
index edef51bf5..f53abebc3 100644
--- a/test/support/factories/accounts_factory.ex
+++ b/test/support/factories/accounts_factory.ex
@@ -13,6 +13,7 @@ defmodule Atomic.Factories.AccountFactory do
%User{
name: Faker.Person.name(),
email: Faker.Internet.email(),
+ handle: Faker.Internet.user_name(),
role: Enum.random(@roles),
hashed_password: Bcrypt.hash_pwd_salt("password1234")
}
From 1d4ab371af0d6fd7e1f497c4e8c3a79526344aa0 Mon Sep 17 00:00:00 2001
From: Rui Lopes <76881129+RuiL1904@users.noreply.github.com>
Date: Sat, 19 Aug 2023 18:21:51 +0100
Subject: [PATCH 3/4] chore: create personalized readme (#331)
---
CODE_OF_CONDUCT.md | 132 +++++++++++++++++++++++++++++++++++++++++++++
README.md | 36 ++++++++-----
2 files changed, 156 insertions(+), 12 deletions(-)
create mode 100644 CODE_OF_CONDUCT.md
diff --git a/CODE_OF_CONDUCT.md b/CODE_OF_CONDUCT.md
new file mode 100644
index 000000000..aa418b3a3
--- /dev/null
+++ b/CODE_OF_CONDUCT.md
@@ -0,0 +1,132 @@
+Contributor Covenant Code of Conduct
+
+## Our Pledge
+
+We as members, contributors, and leaders pledge to make participation in our
+community a harassment-free experience for everyone, regardless of age, body
+size, visible or invisible disability, ethnicity, sex characteristics, gender
+identity and expression, level of experience, education, socio-economic status,
+nationality, personal appearance, race, caste, color, religion, or sexual
+identity and orientation.
+
+We pledge to act and interact in ways that contribute to an open, welcoming,
+diverse, inclusive, and healthy community.
+
+## Our Standards
+
+Examples of behavior that contributes to a positive environment for our
+community include:
+
+* Demonstrating empathy and kindness toward other people
+* Being respectful of differing opinions, viewpoints, and experiences
+* Giving and gracefully accepting constructive feedback
+* Accepting responsibility and apologizing to those affected by our mistakes,
+ and learning from the experience
+* Focusing on what is best not just for us as individuals, but for the overall
+ community
+
+Examples of unacceptable behavior include:
+
+* The use of sexualized language or imagery, and sexual attention or advances of
+ any kind
+* Trolling, insulting or derogatory comments, and personal or political attacks
+* Public or private harassment
+* Publishing others' private information, such as a physical or email address,
+ without their explicit permission
+* Other conduct which could reasonably be considered inappropriate in a
+ professional setting
+
+## Enforcement Responsibilities
+
+Community leaders are responsible for clarifying and enforcing our standards of
+acceptable behavior and will take appropriate and fair corrective action in
+response to any behavior that they deem inappropriate, threatening, offensive,
+or harmful.
+
+Community leaders have the right and responsibility to remove, edit, or reject
+comments, commits, code, wiki edits, issues, and other contributions that are
+not aligned to this Code of Conduct, and will communicate reasons for moderation
+decisions when appropriate.
+
+## Scope
+
+This Code of Conduct applies within all community spaces, and also applies when
+an individual is officially representing the community in public spaces.
+Examples of representing our community include using an official e-mail address,
+posting via an official social media account, or acting as an appointed
+representative at an online or offline event.
+
+## Enforcement
+
+Instances of abusive, harassing, or otherwise unacceptable behavior may be
+reported to the community leaders responsible for enforcement at
+[INSERT CONTACT METHOD].
+All complaints will be reviewed and investigated promptly and fairly.
+
+All community leaders are obligated to respect the privacy and security of the
+reporter of any incident.
+
+## Enforcement Guidelines
+
+Community leaders will follow these Community Impact Guidelines in determining
+the consequences for any action they deem in violation of this Code of Conduct:
+
+### 1. Correction
+
+**Community Impact**: Use of inappropriate language or other behavior deemed
+unprofessional or unwelcome in the community.
+
+**Consequence**: A private, written warning from community leaders, providing
+clarity around the nature of the violation and an explanation of why the
+behavior was inappropriate. A public apology may be requested.
+
+### 2. Warning
+
+**Community Impact**: A violation through a single incident or series of
+actions.
+
+**Consequence**: A warning with consequences for continued behavior. No
+interaction with the people involved, including unsolicited interaction with
+those enforcing the Code of Conduct, for a specified period of time. This
+includes avoiding interactions in community spaces as well as external channels
+like social media. Violating these terms may lead to a temporary or permanent
+ban.
+
+### 3. Temporary Ban
+
+**Community Impact**: A serious violation of community standards, including
+sustained inappropriate behavior.
+
+**Consequence**: A temporary ban from any sort of interaction or public
+communication with the community for a specified period of time. No public or
+private interaction with the people involved, including unsolicited interaction
+with those enforcing the Code of Conduct, is allowed during this period.
+Violating these terms may lead to a permanent ban.
+
+### 4. Permanent Ban
+
+**Community Impact**: Demonstrating a pattern of violation of community
+standards, including sustained inappropriate behavior, harassment of an
+individual, or aggression toward or disparagement of classes of individuals.
+
+**Consequence**: A permanent ban from any sort of public interaction within the
+community.
+
+## Attribution
+
+This Code of Conduct is adapted from the [Contributor Covenant][homepage],
+version 2.1, available at
+[https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1].
+
+Community Impact Guidelines were inspired by
+[Mozilla's code of conduct enforcement ladder][Mozilla CoC].
+
+For answers to common questions about this code of conduct, see the FAQ at
+[https://www.contributor-covenant.org/faq][FAQ]. Translations are available at
+[https://www.contributor-covenant.org/translations][translations].
+
+[homepage]: https://www.contributor-covenant.org
+[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html
+[Mozilla CoC]: https://github.com/mozilla/diversity
+[FAQ]: https://www.contributor-covenant.org/faq
+[translations]: https://www.contributor-covenant.org/translations
diff --git a/README.md b/README.md
index e06ef98d7..37f2966c1 100644
--- a/README.md
+++ b/README.md
@@ -1,20 +1,32 @@
+[contributing]: CONTRIBUTING.md
+[code_of_conduct]: CODE_OF_CONDUCT.md
+[license]: LICENSE.txt
+[ci-style-badge]: https://github.com/cesium/atomic/actions/workflows/style.yml/badge.svg
+[ci-style-link]: https://github.com/cesium/atomic/actions/workflows/style.yml
+[ci-test-badge]: https://github.com/cesium/atomic/actions/workflows/test.yml/badge.svg
+[ci-test-link]: https://github.com/cesium/atomic/actions/workflows/test.yml
+
# Atomic
-To start your Phoenix server:
+> :atom_symbol: De-engineered bifurcated intranet
+
+[![Style CI][ci-style-badge]][ci-style-link]
+[![Test CI][ci-test-badge]][ci-test-link]
+
+## 🤝 Contributing
+
+When contributing to this repository, please first discuss the change you wish to make via issue, email, or any other method with the owners of this repository before making a change.
- * Install dependencies with `mix deps.get`
- * Create and migrate your database with `mix ecto.setup`
- * Start Phoenix endpoint with `mix phx.server` or inside IEx with `iex -S mix phx.server`
+Please note we have a [code of conduct][code_of_conduct], please follow it in all your interactions with the project.
-Now you can visit [`localhost:4000`](http://localhost:4000) from your browser.
+We have a [contributing guide][contributing] to help you get started.
-Ready to run in production? Please [check our deployment guides](https://hexdocs.pm/phoenix/deployment.html).
+## 📝 License
-## Learn more
+
+
- * Official website: https://www.phoenixframework.org/
- * Guides: https://hexdocs.pm/phoenix/overview.html
- * Docs: https://hexdocs.pm/phoenix
- * Forum: https://elixirforum.com/c/phoenix-forum
- * Source: https://github.com/phoenixframework/phoenix
+Copyright (c) 2023 CeSIUM - Centro de Estudantes de Eng. Informática
+This project is licensed under the MIT License - see the [LICENSE][license]
+file for details.
From 6e13421c81cf2cf3b8a939e917b9ced878618bef Mon Sep 17 00:00:00 2001
From: Rui Lopes <76881129+RuiL1904@users.noreply.github.com>
Date: Sat, 19 Aug 2023 18:23:34 +0100
Subject: [PATCH 4/4] chore: improve contributing (#332)
---
CONTRIBUTING.md | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md
index 6227ba921..be3d12846 100644
--- a/CONTRIBUTING.md
+++ b/CONTRIBUTING.md
@@ -11,7 +11,7 @@ The following software is required to be installed on your system:
- [Erlang 25+](https://www.erlang.org/downloads)
- [Elixir 1.14+](https://elixir-lang.org/install.html)
-- [PostgreSQL 13+](https://www.postgresql.org/download/)(^See [this section](#-docker) for setting up with docker.)
+- [PostgreSQL 13+](https://www.postgresql.org/download/)(see [this section](#-docker) for setting up with docker)
We recommend using [asdf version manager][asdf-vm] to install and manage all
the programming languages' requirements.
@@ -25,6 +25,7 @@ First, clone the repository:
```
git clone git@github.com:cesium/atomic.git
cd atomic
+git checkout develop
```
Then, run the setup script to get all dependencies configured. Make sure the database is up and running.
@@ -71,7 +72,7 @@ PostgreSQL up and running.
If you want to setup the required database using docker containers you can
easily do it with [docker-compose](https://docs.docker.com/compose/install/).
-Create and start the database containers.
+Create and start the database containers. You should use `linux.yml` if running on Linux and `darwin.yml` if running on macOS.
```
cp .env.dev.sample .env.dev
@@ -106,3 +107,4 @@ uses.
- [Elixir School Course](https://elixirschool.com/en/)
- [Phoenix Guides Overview](https://hexdocs.pm/phoenix/overview.html)
- [Phoenix Documentation](https://hexdocs.pm/phoenix)
+- [Ecto Documentation](https://hexdocs.pm/ecto)
\ No newline at end of file