├── test ├── test_helper.exs └── cv_amp_json_test.exs ├── mix.lock ├── .gitignore ├── lib ├── cv_amp_json.ex └── template.ex ├── README.md ├── mix.exs ├── LICENSE ├── config └── config.exs ├── cv.json └── index.html /test/test_helper.exs: -------------------------------------------------------------------------------- 1 | ExUnit.start() 2 | -------------------------------------------------------------------------------- /mix.lock: -------------------------------------------------------------------------------- 1 | %{"poison": {:hex, :poison, "2.2.0", "4763b69a8a77bd77d26f477d196428b741261a761257ff1cf92753a0d4d24a63", [:mix], []}} 2 | -------------------------------------------------------------------------------- /test/cv_amp_json_test.exs: -------------------------------------------------------------------------------- 1 | defmodule CvAmpTest do 2 | use ExUnit.Case 3 | doctest CvAmp 4 | 5 | test "the truth" do 6 | assert 1 + 1 == 2 7 | end 8 | end 9 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # The directory Mix will write compiled artifacts to. 2 | /_build 3 | 4 | # If you run "mix test --cover", coverage assets end up here. 5 | /cover 6 | 7 | # The directory Mix downloads your dependencies sources to. 8 | /deps 9 | 10 | # Where 3rd-party dependencies like ExDoc output generated docs. 11 | /doc 12 | 13 | # Ignore .fetch files in case you like to edit your project deps locally. 14 | /.fetch 15 | 16 | # If the VM crashes, it generates a dump, let's ignore it too. 17 | erl_crash.dump 18 | 19 | # Also ignore archive artifacts (built via "mix archive.build"). 20 | *.ez 21 | -------------------------------------------------------------------------------- /lib/cv_amp_json.ex: -------------------------------------------------------------------------------- 1 | defmodule CvAmp do 2 | require Poison 3 | alias Amp.{Template} 4 | @moduledoc """ 5 | Documentation for CvAmp. 6 | """ 7 | 8 | def main(file) do 9 | data = read_JSON(file) 10 | 11 | Template.opening_tags 12 | |> Template.head(data) 13 | |> Template.closing_head_opening_body_tags 14 | |> Template.body(data) 15 | |> Template.closing_tags 16 | |> write_file 17 | end 18 | 19 | def write_file(amp_html) do 20 | File.write!("./index.html", amp_html) 21 | end 22 | 23 | def read_JSON(file) do 24 | 25 | File.read!(file) 26 | |> Poison.Parser.parse! 27 | end 28 | end 29 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # CvAmp 2 | 3 | Generate your CV/resume just using a JSON file... 4 | 5 | See [here](https://jbarget.github.io/cv-amp/) for an example output. 6 | 7 | Anything at all (suggestions, issues), please leave an [issue](https://github.com/jbarget/cv-amp/issues) after checking if what you're about to post doesn't already exist :smile: 8 | ### Getting Started 9 | 10 | **NB Prerequisite:** Elixir already installed 11 | 12 | 1. Clone the repo: `git clone ` 13 | 2. Move into the cv-amp directory: `cd cv-amp` 14 | 3. Get the dependencies: `mix deps.get` 15 | 4. Edit the values in`cv.json` to your info 16 | 5. Open the elixir shell: `iex -S mix` 17 | 6. Run the programme on your JSON file: `CvAmp.main "cv.json"` 18 | 7. You should now have a `index.html` in the root of the directory :tada::tada::tada: 19 | 8. Star the repo :star: 20 | -------------------------------------------------------------------------------- /mix.exs: -------------------------------------------------------------------------------- 1 | defmodule CvAmp.Mixfile do 2 | use Mix.Project 3 | 4 | def project do 5 | [app: :cv_amp, 6 | version: "0.1.0", 7 | elixir: "~> 1.4", 8 | build_embedded: Mix.env == :prod, 9 | start_permanent: Mix.env == :prod, 10 | deps: deps()] 11 | end 12 | 13 | # Configuration for the OTP application 14 | # 15 | # Type "mix help compile.app" for more information 16 | def application do 17 | # Specify extra applications you'll use from Erlang/Elixir 18 | [extra_applications: [:logger]] 19 | end 20 | 21 | # Dependencies can be Hex packages: 22 | # 23 | # {:my_dep, "~> 0.3.0"} 24 | # 25 | # Or git/path repositories: 26 | # 27 | # {:my_dep, git: "https://github.com/elixir-lang/my_dep.git", tag: "0.1.0"} 28 | # 29 | # Type "mix help deps" for more examples and options 30 | defp deps do 31 | [{:poison, "~> 2.0"}] 32 | end 33 | end 34 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Justen Barget 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /config/config.exs: -------------------------------------------------------------------------------- 1 | # This file is responsible for configuring your application 2 | # and its dependencies with the aid of the Mix.Config module. 3 | use Mix.Config 4 | 5 | # This configuration is loaded before any dependency and is restricted 6 | # to this project. If another project depends on this project, this 7 | # file won't be loaded nor affect the parent project. For this reason, 8 | # if you want to provide default values for your application for 9 | # 3rd-party users, it should be done in your "mix.exs" file. 10 | 11 | # You can configure for your application as: 12 | # 13 | # config :cv_amp, key: :value 14 | # 15 | # And access this configuration in your application as: 16 | # 17 | # Application.get_env(:cv_amp, :key) 18 | # 19 | # Or configure a 3rd-party app: 20 | # 21 | # config :logger, level: :info 22 | # 23 | 24 | # It is also possible to import configuration files, relative to this 25 | # directory. For example, you can emulate configuration per environment 26 | # by uncommenting the line below and defining dev.exs, test.exs and such. 27 | # Configuration from the imported file will override the ones defined 28 | # here (which is why it is important to import them last). 29 | # 30 | # import_config "#{Mix.env}.exs" 31 | -------------------------------------------------------------------------------- /cv.json: -------------------------------------------------------------------------------- 1 | { 2 | "title": "Justen's CV", 3 | "basic": { 4 | "first_name": "Justen", 5 | "last_name": "Barget", 6 | "image": "https://avatars1.githubusercontent.com/u/11725595?v=4&u=223c17306393cf8040ab76345ad8666c99360295&s=400", 7 | "intro": "I’m Justen, a Javascript and Elixir developer based in London (happy to work remotely). I love all things code, education, design, 8 | travelling and languages. I am a mentor at the Founders & Coders collective and a 9 | member of the DWYL freelancer community." 10 | }, 11 | "skills": [ "node", "elixir", "phoenix", "react", "redux", "hapi", "express", "AWS", "mongoDB", "redis"], 12 | "education": [{ 13 | "name": "University of Bristol", 14 | "details": "Chemistry, 1st Class Honours" 15 | }], 16 | "projects": [{ 17 | "name": "DWYL - Help Wanted", 18 | "details": "Dashboard to allow users to contribute easily to open source projects", 19 | "stack": "Elixir, Phoenix, Taychons, Postgres" 20 | }, { 21 | "name": "Authored.io", 22 | "details": "A platform to allow journalists to create, curate and deliver content easily", 23 | "stack": "Node (Express), React, Redux" 24 | }, { 25 | "name": "Financial Times - Tag Metrics API", 26 | "details": "A high throughput API to provide consumers with articles' tagging metrics (page views for a tag, trending tags, etc...)", 27 | "stack": "AWS Lambda, Elasticsearch, AWS API Gateway" 28 | }, { 29 | "name": "CvAmp", 30 | "details": "A JSON cv builder that produces mobile-first valid AMP HTML, used to build this CV", 31 | "stack": "Elixir, Taychons" 32 | }, { 33 | "name": "Authored DNI", 34 | "details": "Google funded research project, in conjunction with The Financial Times, into delivering feedback via notifications to improve workflow", 35 | "stack": "Node (Express), AWS Lambda, React, AWS API Gateway" 36 | }, { 37 | "name": "Odysseon", 38 | "details": "Adventure travel platform connecting guides and travellers", 39 | "stack": "Node (Express), React, Alt" 40 | } 41 | ], 42 | "work": [{ 43 | "company": "Emoticast", 44 | "from_to": "Jan 2018 - present", 45 | "details": "Full stack developer working mainly on frontend" 46 | }, { 47 | "company": "Authored", 48 | "from_to": "June 2016 - Jan 2018", 49 | "details": "Full stack developer working across 2 projects" 50 | }, { 51 | "company": "DWYL", 52 | "from_to": "Nov 2016 - present", 53 | "details": "Full stack developer working on multiple projects" 54 | }, { 55 | "company": "No Scrubs", 56 | "from_to": "Nov 2011 - June 2015", 57 | "details": "Founded an events company that ran in 4 cities around the UK" 58 | } 59 | ], 60 | "extra_curricular": [ 61 | "Mentoring: Helped set up and mentor Founders & Coders Nazareth", 62 | "Languages: English, Spanish", 63 | "Cooking: I enjoy cooking a lot" 64 | ], 65 | "references": [{ 66 | "name": "Dan Sofer", 67 | "comment": "Justen, is a first-class developer with a first-class attitude. I can recommend him without reservation." 68 | },{ 69 | "name": "Nelson Correia", 70 | "comment": "Words that comes to mind when I think of Justen: Genuine, natural, talented, can-do, focussed, fast-learner, teacher, humble, patience, quiet, humorous, reliable, punctual, well-spoken, empathetic, caring, team-player, leader. 71 |
72 | He does not fit any text-book 'personality type'. He is well-rounded, grounded and determined and turns his hand to anything in his pursuit of understanding and overcoming a challenge. 73 | He is joy to work with and an asset to any team; I would be delighted to work/learn with him again!" 74 | }] 75 | } 76 | -------------------------------------------------------------------------------- /lib/template.ex: -------------------------------------------------------------------------------- 1 | defmodule Amp.Template do 2 | @moduledoc false 3 | def opening_tags do 4 | """ 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | """ 15 | end 16 | 17 | def get_basic(html, data) do 18 | html <> """ 19 |
20 |
21 | 22 | 25 | 26 |

#{data["first_name"]} #{data["last_name"]}

27 |
28 |

#{data["intro"]}

29 |
30 | """ 31 | end 32 | 33 | def get_skills(html, data) do 34 | skills_html = data 35 | |> Enum.map(fn(skill) -> 36 | """ 37 |
  • #{skill}
  • 38 | """ 39 | end) 40 | |> Enum.join(" ") 41 | 42 | html <> " 44 |
    45 |
    46 | """ 47 | end 48 | 49 | def get_work(html, data) do 50 | work_html = data 51 | |> Enum.map(fn(placement) -> 52 | """ 53 |
    54 |
    55 |

    #{placement["company"]}

    56 |

    #{placement["from_to"]}

    57 |
    58 |

    #{placement["details"]}

    59 |
    60 | """ 61 | end) 62 | |> Enum.join(" ") 63 | 64 | html <> 65 | """ 66 |
    67 |

    Work

    68 |
    69 | """ <> work_html <> "
    " 70 | end 71 | 72 | def get_projects(html, data) do 73 | projects_html = data 74 | |> Enum.map(fn(project) -> 75 | """ 76 |
    77 |
    78 |

    #{project["name"]}:

    79 |

    #{project["stack"]}

    80 |
    81 |

    #{project["details"]}

    82 |
    83 | """ 84 | end) 85 | |> Enum.join(" ") 86 | 87 | html <> 88 | """ 89 |
    90 |

    Projects

    91 |
    92 | """ <> projects_html <> "
    " 93 | end 94 | 95 | def get_education(html, data) do 96 | education_html = data 97 | |> Enum.map(fn(education) -> 98 | """ 99 |
    100 |

    #{education["name"]}

    101 |

    #{education["details"]}

    102 |
    103 | """ 104 | end) 105 | |> Enum.join(" ") 106 | 107 | html <> "

    Education

    " <> education_html <> "
    " 108 | end 109 | 110 | def get_extra_curricular(html, data) do 111 | extra_curricular_html = data 112 | |> Enum.map(fn(extra) -> 113 | """ 114 |
  • #{extra}
  • 115 | """ 116 | end) 117 | |> Enum.join(" ") 118 | 119 | html <> "

    Extra Things

      " <> extra_curricular_html <> "
    " 120 | end 121 | 122 | def get_references(html, data) do 123 | 124 | references_html = data 125 | |> Enum.map(fn(reference) -> 126 | """ 127 |
    128 |

    #{reference["name"]}

    129 |

    #{reference["comment"]}

    130 |
    131 | """ 132 | end) 133 | |> Enum.join(" ") 134 | 135 | html <> "

    References

    " <> references_html <> "
    " 136 | end 137 | 138 | def head(html, data) do 139 | html <> """ 140 | 141 | 142 | #{data["title"]} 143 | """ 144 | end 145 | 146 | def closing_head_opening_body_tags(html) do 147 | html <> """ 148 | 149 | 150 | """ 151 | end 152 | 153 | def body(html, data \\ %{}) do 154 | 155 | get_basic(html, data["basic"]) 156 | |> get_skills(data["skills"]) 157 | |> get_work(data["work"]) 158 | |> get_projects(data["projects"]) 159 | |> get_extra_curricular(data["extra_curricular"]) 160 | |> get_education(data["education"]) 161 | |> get_references(data["references"]) 162 | 163 | end 164 | 165 | def closing_tags(html) do 166 | html <> """ 167 | 168 | 169 | 170 | """ 171 | end 172 | end 173 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | Justen's CV 13 | 14 | 15 |
    16 |
    17 | 18 | 21 | 22 |

    Justen Barget

    23 |
    24 |

    I’m Justen, a Javascript and Elixir developer based in London (happy to work remotely). I love all things code, education, design, 25 | travelling and languages. I am a mentor at the Founders & Coders collective and a 26 | member of the DWYL freelancer community.

    27 |
    28 | 39 |
    40 |
    41 |
    42 |

    Work

    43 |
    44 |
    45 |
    46 |

    Emoticast

    47 |

    Jan 2018 - present

    48 |
    49 |

    Full stack developer working mainly on frontend

    50 |
    51 |
    52 |
    53 |

    Authored

    54 |

    June 2016 - Jan 2018

    55 |
    56 |

    Full stack developer working across 2 projects

    57 |
    58 |
    59 |
    60 |

    DWYL

    61 |

    Nov 2016 - present

    62 |
    63 |

    Full stack developer working on multiple projects

    64 |
    65 |
    66 |
    67 |

    No Scrubs

    68 |

    Nov 2011 - June 2015

    69 |
    70 |

    Founded an events company that ran in 4 cities around the UK

    71 |
    72 |
    73 |

    Projects

    74 |
    75 |
    76 |
    77 |

    DWYL - Help Wanted:

    78 |

    Elixir, Phoenix, Taychons, Postgres

    79 |
    80 |

    Dashboard to allow users to contribute easily to open source projects

    81 |
    82 |
    83 |
    84 |

    Authored.io:

    85 |

    Node (Express), React, Redux

    86 |
    87 |

    A platform to allow journalists to create, curate and deliver content easily

    88 |
    89 |
    90 |
    91 |

    Financial Times - Tag Metrics API:

    92 |

    AWS Lambda, Elasticsearch, AWS API Gateway

    93 |
    94 |

    A high throughput API to provide consumers with articles' tagging metrics (page views for a tag, trending tags, etc...)

    95 |
    96 |
    97 |
    98 |

    CvAmp:

    99 |

    Elixir, Taychons

    100 |
    101 |

    A JSON cv builder that produces mobile-first valid AMP HTML, used to build this CV

    102 |
    103 |
    104 |
    105 |

    Authored DNI:

    106 |

    Node (Express), AWS Lambda, React, AWS API Gateway

    107 |
    108 |

    Google funded research project, in conjunction with The Financial Times, into delivering feedback via notifications to improve workflow

    109 |
    110 |
    111 |
    112 |

    Odysseon:

    113 |

    Node (Express), React, Alt

    114 |
    115 |

    Adventure travel platform connecting guides and travellers

    116 |
    117 |

    Extra Things

    • Mentoring: Helped set up and mentor Founders & Coders Nazareth
    • 118 |
    • Languages: English, Spanish
    • 119 |
    • Cooking: I enjoy cooking a lot
    • 120 |

    Education

    121 |

    University of Bristol

    122 |

    Chemistry, 1st Class Honours

    123 |
    124 |

    References

    125 |

    Dan Sofer

    126 |

    Justen, is a first-class developer with a first-class attitude. I can recommend him without reservation.

    127 |
    128 |
    129 |

    Nelson Correia

    130 |

    Words that comes to mind when I think of Justen: Genuine, natural, talented, can-do, focussed, fast-learner, teacher, humble, patience, quiet, humorous, reliable, punctual, well-spoken, empathetic, caring, team-player, leader. 131 |
    132 | He does not fit any text-book 'personality type'. He is well-rounded, grounded and determined and turns his hand to anything in his pursuit of understanding and overcoming a challenge. 133 | He is joy to work with and an asset to any team; I would be delighted to work/learn with him again!

    134 |
    135 |
    136 | 137 | 138 | --------------------------------------------------------------------------------