diff --git a/.formatter.exs b/.formatter.exs index ef8840c..9f4639b 100644 --- a/.formatter.exs +++ b/.formatter.exs @@ -2,5 +2,9 @@ import_deps: [:ecto, :ecto_sql, :phoenix], subdirectories: ["priv/*/migrations"], plugins: [Phoenix.LiveView.HTMLFormatter], - inputs: ["*.{heex,ex,exs}", "{config,lib,test}/**/*.{heex,ex,exs}", "priv/*/seeds.exs"] + inputs: [ + "*.{heex,ex,exs}", + "{core,extensions,config,lib,test}/**/*.{heex,ex,exs}", + "priv/*/seeds.exs" + ] ] diff --git a/config/config.exs b/config/config.exs index 87faebb..f8e9757 100644 --- a/config/config.exs +++ b/config/config.exs @@ -9,7 +9,8 @@ import Config config :phoenix_extensions, ecto_repos: [PhoenixExtensions.Repo], - generators: [timestamp_type: :utc_datetime] + generators: [timestamp_type: :utc_datetime], + extensions: [PhoenixExtensions.Extensions.TelegramBot] # Configures the endpoint config :phoenix_extensions, PhoenixExtensionsWeb.Endpoint, @@ -64,3 +65,8 @@ config :phoenix, :json_library, Jason # Import environment specific config. This must remain at the bottom # of this file so it overrides the configuration defined above. import_config "#{config_env()}.exs" + +# Import Telegram Bot Extension Config +import_config ["extensions", "telegram_bot", "config", "#{config_env()}.exs"] + |> Path.join() + |> Path.expand() diff --git a/core/.formatter.exs b/core/.formatter.exs new file mode 100644 index 0000000..d2cda26 --- /dev/null +++ b/core/.formatter.exs @@ -0,0 +1,4 @@ +# Used by "mix format" +[ + inputs: ["{mix,.formatter}.exs", "{config,lib,test}/**/*.{ex,exs}"] +] diff --git a/core/.gitignore b/core/.gitignore new file mode 100644 index 0000000..17ce19a --- /dev/null +++ b/core/.gitignore @@ -0,0 +1,23 @@ +# The directory Mix will write compiled artifacts to. +/_build/ + +# If you run "mix test --cover", coverage assets end up here. +/cover/ + +# The directory Mix downloads your dependencies sources to. +/deps/ + +# Where third-party dependencies like ExDoc output generated docs. +/doc/ + +# If the VM crashes, it generates a dump, let's ignore it too. +erl_crash.dump + +# Also ignore archive artifacts (built via "mix archive.build"). +*.ez + +# Ignore package tarball (built via "mix hex.build"). +core-*.tar + +# Temporary files, for example, from tests. +/tmp/ diff --git a/core/lib/core.ex b/core/lib/core.ex new file mode 100644 index 0000000..1c53942 --- /dev/null +++ b/core/lib/core.ex @@ -0,0 +1,18 @@ +defmodule Core do + @moduledoc """ + Documentation for `Core`. + """ + + @doc """ + Hello world. + + ## Examples + + iex> Core.hello() + :world + + """ + def hello do + :world + end +end diff --git a/core/mix.exs b/core/mix.exs new file mode 100644 index 0000000..9c748e1 --- /dev/null +++ b/core/mix.exs @@ -0,0 +1,28 @@ +defmodule Core.MixProject do + use Mix.Project + + def project do + [ + app: :phoenix_extensions_core, + version: "0.1.0", + elixir: "~> 1.18", + start_permanent: Mix.env() == :prod, + deps: deps() + ] + end + + # Run "mix help compile.app" to learn about applications. + def application do + [ + extra_applications: [:logger] + ] + end + + # Run "mix help deps" to learn about dependencies. + defp deps do + [ + # {:dep_from_hexpm, "~> 0.3.0"}, + # {:dep_from_git, git: "https://github.com/elixir-lang/my_dep.git", tag: "0.1.0"} + ] + end +end diff --git a/core/test/core_test.exs b/core/test/core_test.exs new file mode 100644 index 0000000..661aff1 --- /dev/null +++ b/core/test/core_test.exs @@ -0,0 +1,8 @@ +defmodule CoreTest do + use ExUnit.Case + doctest Core + + test "greets the world" do + assert Core.hello() == :world + end +end diff --git a/core/test/test_helper.exs b/core/test/test_helper.exs new file mode 100644 index 0000000..869559e --- /dev/null +++ b/core/test/test_helper.exs @@ -0,0 +1 @@ +ExUnit.start() diff --git a/extensions/telegram_bot/.formatter.exs b/extensions/telegram_bot/.formatter.exs new file mode 100644 index 0000000..d2cda26 --- /dev/null +++ b/extensions/telegram_bot/.formatter.exs @@ -0,0 +1,4 @@ +# Used by "mix format" +[ + inputs: ["{mix,.formatter}.exs", "{config,lib,test}/**/*.{ex,exs}"] +] diff --git a/extensions/telegram_bot/.gitignore b/extensions/telegram_bot/.gitignore new file mode 100644 index 0000000..40c6054 --- /dev/null +++ b/extensions/telegram_bot/.gitignore @@ -0,0 +1,23 @@ +# The directory Mix will write compiled artifacts to. +/_build/ + +# If you run "mix test --cover", coverage assets end up here. +/cover/ + +# The directory Mix downloads your dependencies sources to. +/deps/ + +# Where third-party dependencies like ExDoc output generated docs. +/doc/ + +# If the VM crashes, it generates a dump, let's ignore it too. +erl_crash.dump + +# Also ignore archive artifacts (built via "mix archive.build"). +*.ez + +# Ignore package tarball (built via "mix hex.build"). +extension_telegram_bot-*.tar + +# Temporary files, for example, from tests. +/tmp/ diff --git a/extensions/telegram_bot/README.md b/extensions/telegram_bot/README.md new file mode 100644 index 0000000..04e54fc --- /dev/null +++ b/extensions/telegram_bot/README.md @@ -0,0 +1,21 @@ +# ExtensionTelegramBot + +**TODO: Add description** + +## Installation + +If [available in Hex](https://hex.pm/docs/publish), the package can be installed +by adding `extension_telegram_bot` to your list of dependencies in `mix.exs`: + +```elixir +def deps do + [ + {:extension_telegram_bot, "~> 0.1.0"} + ] +end +``` + +Documentation can be generated with [ExDoc](https://github.com/elixir-lang/ex_doc) +and published on [HexDocs](https://hexdocs.pm). Once published, the docs can +be found at . + diff --git a/extensions/telegram_bot/config/dev.exs b/extensions/telegram_bot/config/dev.exs new file mode 100644 index 0000000..e69de29 diff --git a/extensions/telegram_bot/config/prod.exs b/extensions/telegram_bot/config/prod.exs new file mode 100644 index 0000000..e69de29 diff --git a/extensions/telegram_bot/config/test.exs b/extensions/telegram_bot/config/test.exs new file mode 100644 index 0000000..e69de29 diff --git a/extensions/telegram_bot/lib/extension.ex b/extensions/telegram_bot/lib/extension.ex new file mode 100644 index 0000000..e3c9c5f --- /dev/null +++ b/extensions/telegram_bot/lib/extension.ex @@ -0,0 +1,10 @@ +defmodule PhoenixExtensions.Extensions.TelegramBot do + @moduledoc false + + require Logger + + def init() do + Logger.info("Telegram Bot Extension Initialized") + :ok + end +end diff --git a/extensions/telegram_bot/lib/web/controllers/controller.ex b/extensions/telegram_bot/lib/web/controllers/controller.ex new file mode 100644 index 0000000..e69de29 diff --git a/extensions/telegram_bot/lib/web/router.ex b/extensions/telegram_bot/lib/web/router.ex new file mode 100644 index 0000000..e69de29 diff --git a/extensions/telegram_bot/mix.exs b/extensions/telegram_bot/mix.exs new file mode 100644 index 0000000..bd0065f --- /dev/null +++ b/extensions/telegram_bot/mix.exs @@ -0,0 +1,30 @@ +defmodule PhoenixExtensions.Extensions.TelegramBot.MixProject do + use Mix.Project + + def project do + [ + app: :extension_telegram_bot, + version: "0.1.0", + elixir: "~> 1.18", + start_permanent: Mix.env() == :prod, + deps: deps() + ] + end + + # Run "mix help compile.app" to learn about applications. + def application do + [ + extra_applications: [:logger] + ] + end + + # Run "mix help deps" to learn about dependencies. + defp deps do + [ + {:phoenix_extensions_core, path: Path.expand(Path.join(["..", "..", "core"]))}, + {:phoenix, "~> 1.7.18"} + # {:dep_from_hexpm, "~> 0.3.0"}, + # {:dep_from_git, git: "https://github.com/elixir-lang/my_dep.git", tag: "0.1.0"} + ] + end +end diff --git a/extensions/telegram_bot/test/telegram_bot_test.exs b/extensions/telegram_bot/test/telegram_bot_test.exs new file mode 100644 index 0000000..4578924 --- /dev/null +++ b/extensions/telegram_bot/test/telegram_bot_test.exs @@ -0,0 +1,8 @@ +defmodule PhoenixExtensions.Extensions.TelegramBotTest do + use ExUnit.Case + doctest ExtensionTelegramBot + + test "greets the world" do + assert ExtensionTelegramBot.hello() == :world + end +end diff --git a/extensions/telegram_bot/test/test_helper.exs b/extensions/telegram_bot/test/test_helper.exs new file mode 100644 index 0000000..869559e --- /dev/null +++ b/extensions/telegram_bot/test/test_helper.exs @@ -0,0 +1 @@ +ExUnit.start() diff --git a/lib/phoenix_extensions/application.ex b/lib/phoenix_extensions/application.ex index 3a2d6ac..591a441 100644 --- a/lib/phoenix_extensions/application.ex +++ b/lib/phoenix_extensions/application.ex @@ -11,9 +11,9 @@ defmodule PhoenixExtensions.Application do PhoenixExtensionsWeb.Telemetry, PhoenixExtensions.Repo, {Ecto.Migrator, - repos: Application.fetch_env!(:phoenix_extensions, :ecto_repos), - skip: skip_migrations?()}, - {DNSCluster, query: Application.get_env(:phoenix_extensions, :dns_cluster_query) || :ignore}, + repos: Application.fetch_env!(:phoenix_extensions, :ecto_repos), skip: skip_migrations?()}, + {DNSCluster, + query: Application.get_env(:phoenix_extensions, :dns_cluster_query) || :ignore}, {Phoenix.PubSub, name: PhoenixExtensions.PubSub}, # Start the Finch HTTP client for sending emails {Finch, name: PhoenixExtensions.Finch}, @@ -23,6 +23,11 @@ defmodule PhoenixExtensions.Application do PhoenixExtensionsWeb.Endpoint ] + # Initialize extensions + Enum.each(Application.get_env(:phoenix_extensions, :extensions, []), fn extension -> + extension.init() + end) + # See https://hexdocs.pm/elixir/Supervisor.html # for other strategies and supported options opts = [strategy: :one_for_one, name: PhoenixExtensions.Supervisor] diff --git a/mix.exs b/mix.exs index dd2acc3..95d94c4 100644 --- a/mix.exs +++ b/mix.exs @@ -27,6 +27,13 @@ defmodule PhoenixExtensions.MixProject do defp elixirc_paths(:test), do: ["lib", "test/support"] defp elixirc_paths(_), do: ["lib"] + # Specifies your project extensions. + defp extensions do + [ + {:extension_telegram_bot, path: Path.join(["extensions", "telegram_bot"])} + ] + end + # Specifies your project dependencies. # # Type `mix help deps` for examples and options. @@ -58,7 +65,7 @@ defmodule PhoenixExtensions.MixProject do {:jason, "~> 1.2"}, {:dns_cluster, "~> 0.1.1"}, {:bandit, "~> 1.5"} - ] + ] ++ extensions() end # Aliases are shortcuts or tasks specific to the current project. diff --git a/test/phoenix_extensions_web/controllers/error_html_test.exs b/test/phoenix_extensions_web/controllers/error_html_test.exs index 2fcc5f0..6f23286 100644 --- a/test/phoenix_extensions_web/controllers/error_html_test.exs +++ b/test/phoenix_extensions_web/controllers/error_html_test.exs @@ -9,6 +9,7 @@ defmodule PhoenixExtensionsWeb.ErrorHTMLTest do end test "renders 500.html" do - assert render_to_string(PhoenixExtensionsWeb.ErrorHTML, "500", "html", []) == "Internal Server Error" + assert render_to_string(PhoenixExtensionsWeb.ErrorHTML, "500", "html", []) == + "Internal Server Error" end end diff --git a/test/phoenix_extensions_web/controllers/error_json_test.exs b/test/phoenix_extensions_web/controllers/error_json_test.exs index 0d6beac..6d21e04 100644 --- a/test/phoenix_extensions_web/controllers/error_json_test.exs +++ b/test/phoenix_extensions_web/controllers/error_json_test.exs @@ -2,7 +2,9 @@ defmodule PhoenixExtensionsWeb.ErrorJSONTest do use PhoenixExtensionsWeb.ConnCase, async: true test "renders 404" do - assert PhoenixExtensionsWeb.ErrorJSON.render("404.json", %{}) == %{errors: %{detail: "Not Found"}} + assert PhoenixExtensionsWeb.ErrorJSON.render("404.json", %{}) == %{ + errors: %{detail: "Not Found"} + } end test "renders 500" do