{"id":19959349,"url":"https://github.com/tbrlpld/log100days","last_synced_at":"2025-07-16T01:07:18.474Z","repository":{"id":102978337,"uuid":"249283769","full_name":"tbrlpld/log100days","owner":"tbrlpld","description":"Containerized Quart app to display a markdown log for the #100DaysOfCode challenge as a website","archived":false,"fork":false,"pushed_at":"2020-09-05T07:51:12.000Z","size":46,"stargazers_count":3,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-07-14T06:18:25.473Z","etag":null,"topics":["100daysofcode","docker","flask","quart"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/tbrlpld.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2020-03-22T22:24:17.000Z","updated_at":"2023-03-07T08:19:15.000Z","dependencies_parsed_at":null,"dependency_job_id":"44a64864-a9ae-4498-b806-1c38e3a7225a","html_url":"https://github.com/tbrlpld/log100days","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/tbrlpld/log100days","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tbrlpld%2Flog100days","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tbrlpld%2Flog100days/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tbrlpld%2Flog100days/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tbrlpld%2Flog100days/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/tbrlpld","download_url":"https://codeload.github.com/tbrlpld/log100days/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/tbrlpld%2Flog100days/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":265472746,"owners_count":23771947,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["100daysofcode","docker","flask","quart"],"created_at":"2024-11-13T01:47:22.899Z","updated_at":"2025-07-16T01:07:18.461Z","avatar_url":"https://github.com/tbrlpld.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Log100Days\n\nThis is a small Quart app to render a #100DayOfCode markdown log as a HTML page.\nQuart is an async-enabled version of Flask.\n\nI have also created a [Gatsby site with the same functionality](https://github.com/tbrlpld/log100days-gatsby),\nbecause it is overkill to do the conversion from markdown to HTML on every request for content that is only updated once a day.\n\n## Usage\n\nThis app is designed to be pointed at the raw files of #100DayOfCode markdown journal repository.\nYou can clone/fork [@kallaway's original journal repo](https://github.com/kallaway/100-days-of-code) to start your log.\n\nTo find the URL for the raw files click one of the files and then the \"Raw\" button.\nThis will give you a URL like this: `https://raw.githubusercontent.com/kallaway/100-days-of-code/master/README.md`\n\nYou only need the part until the filename: `https://raw.githubusercontent.com/kallaway/100-days-of-code/master/`\n\nThe app will generate a HTML based on the content of the Markdown files in the repo.\nYou can see a [live implementation on my website](https://log100days.lpld.io).\n\n## Requirements\n\nRequires a host (or local machine) with [Docker](https://docs.docker.com/install/) installed.\n\n## Installation\n\nIf you have `docker` installed, you don't really need to install anything.\nAll you need is to pull the Docker image.\n```sh\n$ docker pull tbrlpld/log100days\n```\n\nDepending on your OS and setup, you might have to run the docker with `sudo`.\n\n\n## Configuration\n\nIf you try to run the app container with out configuring the app first, you will get an error message.\n```sh\n$ docker run tbrlpld/log100days\n...\nKeyError: 'The environment variable SECRET_KEY is missing. Be sure to configure it and try again.'\n```\n\nTo enable configuration of the app running in the container, we are using environment variables.\nThe advantage over file based configuration is that environment variables can be created in the\ncontainer in different ways.\n\nYou can [pass environment variables to the container via the `docker-compose` file](https://docs.docker.com/compose/compose-file/#environment),\nor directly [to the `docker run` command](https://docs.docker.com/engine/reference/commandline/run/#set-environment-variables--e---env---env-file).\nInstead of creating each environment variable separately, you can also make use of [environment files](https://docs.docker.com/compose/compose-file/#environment#env_file) in either of these cases.\n\nTo make the environment variables easy to reuse, we use the environment file approach.\nThis can be done by creating a `.env` file with the following content:\n```\nSECRET_KEY=this-needs-to-be-something-safe\nMARKDOWN_LOG_URL=https://raw.githubusercontent.com/kallaway/100-days-of-code/master/\nHOME_URL=https://example.com\n```\n\nMake sure to use a safe value for the `SECRET_KEY` environment variable and **do not commit it to version control**.\n\nThe `MARKDOWN_LOG_URL` settings defines the repository where the markdown files can be found.\nIt does not have to be a GitHub repo.\nAny URL which is extended with the Markdown filenames works.\n\nThe `HOME_URL` defines which site the \"Home\" link in the navigation menu should point to.\nIf this setting is not defined, the menu entry is omitted.\n\nNow the use of the environment file needs to be passed to docker.\nTo do so, just add the `env_file` key to the `docker-compose.yml`.\n```yml\n        ...\n        env_file:\n          - .env\n        ...\n```\n\n**Alternative Configuration**\n\nThe more Flask typical way of configuring through a `config.py` file in the \"instance\" folder is still possible.\nThe values defined in the `config.py` will override what is defined in the environment variables.\n\nSince the configuration file is a Python file, use the appropriate syntax to define the values.\nSee the Flask documentation on [more information on how to use these configuration files](https://flask.palletsprojects.com/en/1.1.x/config/#configuring-from-files).\n\nCopy the `config.py` file to the `/usr/src/app/instance` folder on the container.\nThis can be achieved by [mounting a volume](https://docs.docker.com/compose/compose-file/#volumes) at the appropriate location.\n\n## Run the App\n\nWith the configuration file in place, you can run the app like so:\n```sh\n$ docker run -d --env-file .env -p 127.0.0.1:5000:5000 tbrlpld/log100days\n```\n\nTo document this command and simplify how to start the app, you can use a `docker-compose.yml` file.\nJust like the [`docker-compose.yml` file](./docker-compose.yml) here in this repo.\n\nThis simplifies the start up command to the following, when you are in the working directory of the `docker-compose.yml` file.\n```sh\n$ docker-compose up -d\n```\n\nTo stop the service, run the following in the directory with the `docker-compose.yml` file.\n```\n$ docker-compose stop\n```\n\n*Attention* The `docker-compose.yml` file in this repo makes the container only available from the host.\nThis is, because I think this is a good security practice.\nIf you do not define the host do be only localhost, then Docker will adjust your IP tables and let outside traffic through to the container.\n\nTo achieve outside access to the app while running it only for the localhost, you can use a [reverse proxy like NGINX](https://docs.nginx.com/nginx/admin-guide/web-server/reverse-proxy/).\nAn example site NGINX config is in the repo.\nThis file only needs to be copied/linked to `/etc/nginx/sites-enabled` to enable a basic proxy forwarding from a running NGINX instance to the locally available container.\n\n\n## Development\n\n### Configure and Run the App in Development\n\nThis app utilizes Docker containers for development and deployment.\n\nDuring development you are going to want to update the source code often and see the changes on the page.\nTo achieve this with a containerized app, you want to override the source directory in the container with the one on your machine (the docker host).\n\n```sh\n$ docker run -v /Users/tibor/1-Projects/log100days:/usr/src/app -p 127.0.0.1:5000:5000 tbrlpld/log100days:latest\n```\n\nIn the above example, the app directory in the container (`/usr/src/app`) is overridden by mounting the source directory on the host (e.g. `/Users/tibor/1-Projects/log100days`) to its location.\n\nNow you can change the source code locally and the the changes are immediately available in the container.\n\nYou might not see the changes populate through to the app in the browser.\nThis is because, by default, the container is running the production server.\nThe production loads the app once on start up.\nFurther changes do no go through.\n\nTo see the changes during without having the stop and start the server, or container, you can run the development server.\nThe development server in the container can be started with the `--entrypoint` command line flag.\n\n```sh\n$ docker run  --entrypoint quart -v /Users/tibor/1-Projects/log100days:/usr/src/app -p 127.0.0.1:5000:5000 tbrlpld/log100days run -h 0 -p 5000\n```\n\nNote that the executable (`quart`) and the arguments (in this case `run`) are not written directly after one another.\nBe sure to also configure the `quart` development server to accept connections from other hosts than localhost.\nOnly accepting connections from localhost would mean only accepting from inside the container.\n\nThe `quart` development server also requires the environment variables `QUART_APP` and `QUART_DEBUG` to be present.\nFor this app and development, set `QUART_APP=log100days:app` and `QUART_DEBUG=1`.\nThese environment variables can be added to the environment file `.env` used for configuration of the app (see the [Configuration section](#configuration) for more information).\nUse the `--env-flag` to pass the environment variables from the environment file to the container.\n\n```sh\n$ docker run  --entrypoint quart --env-file .env -v /Users/tibor/1-Projects/log100days:/usr/src/app -p 127.0.0.1:5000:5000 tbrlpld/log100days run -h 0 -p 5000\n```\n\nSince this is quite the line, you might want to save this somehow.\nThis is where [`docker-compose`](https://docs.docker.com/compose/compose-file/) comes in.\n\nThere already is a `docker-compose.yml` file in the repo for production use.\nBut you can go ahead an create your own file with settings for local development.\nSee [`docker-compose document`](https://docs.docker.com/compose/compose-file/) for the syntax and available options.\n\nYou can run `docker-compose` with a different file than the default (`docker-compose.yml`) by using the `-f` flag.\n\n```sh\n$ docker-compose -f docker-compose-dev.yml up\n```\n\n### Build and Distribute\n\nRun the following command to build the latest image version using the production settings.\n```sh\n$ docker-compose build\n...\nSuccessfully tagged tbrlpld/log100days:latest\n```\n\nThen tag this image with a version.\nMake sure this is a new unused version number.\n```sh\n$ docker tag tbrlpld/log100days:latest tbrlpld/log100days:0.1\n```\n\nPush all the latest build images to DockerHub.\n```sh\n$ docker push tbrlpld/log100days\n```\n\nBuilds can also be automated on [DockerHub](https://docs.docker.com/docker-hub/builds/) by following a certain branch on GitHub.\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftbrlpld%2Flog100days","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ftbrlpld%2Flog100days","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ftbrlpld%2Flog100days/lists"}