By Developers, For Developers
PDF Pg | Paper Pg | Type | Description | Fixed on | Comments |
---|---|---|---|---|---|
9 | ERROR | Output should start at 0 after `run/2` called with `f` and `0`. | 2019-04-30 | ||
10 | ERROR | iex return value for start function has old return value: | 2019-04-30 | ||
10 | ERROR | iex(1)> counter_pid = Counter.start(0) #PID<0.112.0> | 2019-04-30 | ||
26 | TYPO | last paragraph may be missing something, starts as “and a predetermined”. | 2019-04-30 | ||
38 | ERROR | The description says that some characters take two bytes, but the diagram seems to indicate a character of three bytes (the ellipses). | 2019-06-29 | The é is two bytes, but I'll add a small clarification. | |
ix | TYPO | > Find James at @geg2 James’ twitter user name is wrong. It should be @JEG2 | 2019-04-30 | ||
16 | TYPO | In a second item of the numbered list, there’s a word “with” used twice as “with with”. | 2019-04-30 | ||
8 | SUGGEST | I’ve never taken part in an escape room challenge but the idea of running out of time and ‘calling for our first clue’ doesn’t make sense to me. Were you asking for the last clue? In the next sentence you mention ‘this last bit of information’ so it is probably just a typo. | 2019-04-30 | ||
53 | ERROR | We’ll create a lib/core directory to hold the modules with our data layer (and later our core functions). | 2019-04-30 | ||
3 | TYPO | Original text: The next component, a project called Mastery. will be much more complex, I believe the dot after Mastery (“Mastery.”) is incorrect. | 2019-04-30 | ||
4 | TYPO | Original text: At this stage, you’re first goal is to understand Maybe It should be ? … “At this stage, your first goal is to understand” (your, instead of you’re) | 2019-04-30 | ||
5 | TYPO | Original text: Our focus will be primarily in three areas. (and then displays a list of three bullet points) Other parts of the book use “:” before a list of bullet points, but here is different, it’s using a final hard dot. | 2019-04-30 | ||
29 | SUGGEST | At the end of the discussion of structs it says: “In this book, we’ll use structs primarily for internal interfaces, except when we’re building common infrastructure.” Could you add a small example, or perhaps a pointer to another part of the book where this principle is put into practice? I found this sentence to be unclear (perhaps, in part, because I come from a world where “infrastructure” refers to machines and networks and the like). | 2019-04-30 | ||
3 | DEFER | I was really confused to have been introduced to the names of the layers, but not their definitions, and then transition immediately into building some code. What was missing for me was a simple description of what each of the layers meant. I think a short bullet chart with one or two sentences about what each layer was for would have been handy. THEN introduce the projects and discuss how each will tie back to those definitions. | 2019-09-09 | We will collect comments like this and prioritize them, getting to as many as we can. | |
9 | TYPO | At the top of the page you say, “Crack open lib/counter/lib/counter/server.ex and key this in:” I think the path should be: lib/counter/server.ex | 2019-04-30 | ||
9 | SUGGEST | The GettingStarted/counter/lib/counter.ex code is split over two pages in the PDF but in the ePub and downloaded code there is an empty line where this happens (after ‘receive do’) and it may be a result of the PDF code’s layout. However if you run ‘mix format’ against the code with the empty line after ‘receive do’ it removes it. So, my suggestion for this (and all of the code samples) would be to run it against ‘mix format’ to standardise it. For better or worse we now have a code formatter and I think that adhering to its rules would be a good thing for sample code. | 2019-04-30 | I don't think we're going to do this. Good comment, but books are a special case and I think we want to control the formatting closely. | |
15 | SUGGEST | Towards the bottom of the page you say, “There you have it. Our counter is done and you’ve seen all of our layers. Let’s wrap up, and then we’ll be ready to introduce the layers step by step.” However this chapter was an introduction to the layers so parhaps say something like, “There you have it. Our counter is done and you’ve seen all of our layers. Let’s wrap up, and then we’ll be ready to go into more detail about each layer in turn.” | 2019-04-30 | ||
24 | TYPO | In “Random Access in Lists” paragraph, | 2019-04-30 | ||
5 | TYPO | James Twitter Handle is | 2019-04-30 | ||
109 | ERROR | > Let’s write our first cast callback, the one to build a quiz: This line says we are going to write a cast callback but the following example is for a call callback. > Boundary/lib/mastery/boundary/quiz_manager.ex | 2019-04-30 | ||
110 | ERROR | > This final cast looks up a quiz and return it to the user. 1. This line refers a a cast but the example before this line was for a call. | 2019-04-30 | ||
25 | TYPO | The first diagram seems to be the same as the second and is probably the wrong one. In case it isn’t, I found it confusing as an explanation for what you wanted to do to the list. | 2019-04-30 | ||
24 | TYPO | In the last line you say that you want to add an item to the list. You then explain how you replace an item in the list. | 2019-04-30 | ||
82 | SUGGEST | In the sentence: “We use Map.fetch! because we want to…” you write Map.fetch!, but the first listing on the page (Tests/test/support/quiz_builders.exs) uses Keyword.fetch!. Maybe just write “fetch!” or “Keyword.fetch!” | 2019-04-30 | ||
45 | TYPO | The diagram on this page hasn’t been reproduced properly in the ePub or Kindle versions of the book. I realise that this will eventually be sorted out as a publishing issue (along with general image quality issues in these formats too) but it might be an easy fix for the next beta. | 2019-04-30 | you might be seeing the stacked boxes, meaning multiple instances. | |
25 | ERROR | The section on lists states: “Streams provide some wonderful properties because Elixir is a lazy language.” | 2019-04-30 | ||
48 | TYPO | name of file should be lib/mastery/core/response.ex not lib/mastery/respone.ex | 2019-04-30 | ||
16 | TYPO | “2. A function invoked with with the same inputs” -> “A function invoked with the same inputs” | 2019-04-30 | ||
87 | ERROR | The test “a timestamp is added at build time” incorrectly compares DateTime structures with “<”: assert response.timestamp < DateTime.utc_now() DateTimes should be compared with the “compare” function, as per the DateTime documentation. | 2019-04-30 | we'll handle code changes in a later beta | |
6 | TYPO | point 2 of that page: A function invoked with with … | 2019-04-30 | ||
1 | OK | I find the reference to “do fun things with… something” confusing and annoying. I don’t think anyone needs that analogy. You can safely assume your audience is familiar with the concepts described in the book. No need for that extra layer. | 2019-04-30 | ||
65 | TYPO | The last paragraph starts with, “Then pick_current_question adds that list to a quiz.” It’s adding a question however, not a list. | 2019-04-30 | ||
66 | TYPO | On the paragraph below the first code block you say, “Moving a template to used or any other field is the same, so we generalize the concept. We remove the quiz from the quiz.templates list and then add it to the specified field of quiz.” The second sentence should be, I think, “We remove the template from the quiz.templates…” | 2019-04-30 | ||
9 | ERROR | “Here’s the magic. The receive message allows us to interact with the server at each iteration of the loop.” I wouldn’t refer to the receive block as a message. If “block” isn’t a good enough abstraction, I would then refer to it as the receive “mailbox”. | 2019-04-30 | ||
9 | SUGGEST | A chapter 1 code example of “Establish Your Boundaries” could be made simpler without losing the point of the discussion. | 2019-06-29 | Whenever I have to repeat an operation over and over again, I prefer to separate the operation from the loop. The two main reasons for this are that it keeps each chunk of code worrying about just one thing and it also makes testing much easier since you can trigger individual steps as needed. | |
12 | SUGGEST | The last sentence of the first paragraph of section “Keep Your Functional Core Separate”. Something about combining “share our data” and an isolated OTP process in the same sentence feels O-Oish to me. | 2019-06-29 | \nGood point. Let me think about this one. | |
10 | TYPO | The iex(2) line is missing the “iex(2)>” prompt. The call for Counter.state/1 is partially missing and has “.Api” in it as well. It should be “iex(2)> Counter.state(counter_pid)” | 2019-04-30 | ||
57 | TYPO | ‘reexamine’ in paragraph 2 should be hyphenated. | 2019-04-30 | ||
57 | TYPO | In the 3rd paragraph you say, “… and a checker functions to test results.” This should either be ‘and checker functions’ or ‘and a checker function’ | 2019-04-30 | ||
57 | TYPO | The last paragraph starts with, “EEX is a module used to compile idiomatic Elixir templates…”. The opening EEX should be EEx. | 2019-04-30 | ||
57 | TYPO | In the last paragraph you say, “Though our template looked complex at the surface…”. On the surface is more usual. | 2019-04-30 | ||
102 | TYPO | In the second paragraph you say, "… and the external systems our boundary might uses can fail. Uses should be use. | 2019-04-30 | ||
58 | TYPO | The second paragraph begins with, “We will need to use the template to generate the question text we put in asked, and we’ll store the template we use to generate a question, as well as the substitutions we’ll choose from.” The substitutions store the chosen values, not the values we can choose from. Maybe change to, “… as well as the substitutions we chose.” | 2019-04-30 | ||
78 | TYPO | The first new paragraph on the page starts with: “Fixtures are constructors. They are convenience functions that return complex data project-specific structures for the purposes of tests.” It would read better as: “Fixtures are constructors. They are convenience functions that return complex, project-specific, data structures for the purposes of tests.” | 2019-04-30 | ||
79 | OK | At the end of the quiz_builders.exs code block add a final ‘end’. | 2019-04-30 | This is actually part of another listing. We break longer listings into pieces. | |
1 | OK | The mnemonic isn’t working for me and seems to be in the way all over the text. It leads to things like diagrams with “Loud” and “Wildebeest” in them. Why? When you break it down to that level “loud” has absolutely nothing to do with “lifecycle.” It was supposed to be a helpful way to remember 6 words, but now it’s everywhere in the text itself. The mnemonic is neither helpful nor needed. In a book targeting experts the six concepts are already quite familiar. The alternate six words are just a mess when they’re used. Take page 22 for example. If you read the presumably important first words in the diagram you get “Loud, Wildebeests, Big, Fun, Do.” What? Compare this to simply labeling them “Lifecycle, Workers, Boundaries, Functions, Data.” I realize that those are also in there, but they’re hiding behind this set of words that are supposed to be helping. It’s clutter. | 2019-04-30 | ||
10 | TYPO | Missing iex(2)> in interactive example | 2019-04-30 | ||
10 | TYPO | On the runtime example: | 2019-04-30 | ||
23 | ERROR | “Atoms are quite efficient, taking a single byte, plus a lookup table.” Atoms use 1 word plus a lookup table, not 1 byte. | 2019-04-30 | ||
33 | SUGGEST | This paragraph is probably worth the price of admission: However it leaves me hanging. Despite the footnote, I don’t know what the ‘far reaching implications’ are. And I really want to know. Consider expanding this point. (Great work so far) | 2019-06-29 | We will think about this one. | |
34 | TYPO | We emphasizing the need to access lists head first. | 2019-04-30 | ||
59 | SUGGEST | This is the worst kind of errata… Joe needs to be referred to in the past. “Joe Armstrong, one of the creators of Erlang, used to say that we’re always taking the data to the code…” | 2019-04-30 | ||
28 | SUGGEST | This also occurs on page 59 but you refer to a “two-tuple” which might be normal but seemed odd to me. A two-element tuple sounds better, | 2019-04-30 | ||
5 | TYPO | In: “Just as an artist needs to learn to use the colors on their palate”, palate shouldn’t be palette? | 2019-04-30 | ||
1-15 | SUGGEST | I think the structuring of the concepts (Data, Functions, Tests, Boundaries, Process Lifecycle, Process Deployment) valuable | 2019-04-30 | ||
41 | SUGGEST | As we describe the problem, think about the nouns, those will be Data.. (p 41.), | 2019-04-30 | ||
41ff | SUGGEST | Explanation of data use (Prefer Flat Data to Deep Ones) is good. | 2019-06-29 | This section has improved a lot, since this comment was made. I suspect it's better now. | |
34 | 26 | TYPO | Looks like some text is missing or there is an unintentional paragraph break. The end of the page is: "The defstruct macro adds the struct function to User with two arities. The zero arity function creates a default struct and the second takes a list of key- value pairs. and a predetermined list of attributes, :name and :email. One capability of structs that’s often missed is the @enforce_keys module attribute. You can use it to" | 2019-04-30 | |
118 | 115 | SUGGEST | “We alias the only two functions we need” should probably be “We alias the only two modules we need” | 2019-04-30 | |
124 | 121 | SUGGEST | I believe the API layer is reaching too deep into the GenServers. - Out of place: in Boundary/lib/mastery.ex: def start_quiz_manager(opts), do: QuizManager.start_link(opts) This would require you to have a start_link function in the QuizManager module, which also feels more naturally. - Reaching too deep: Boundary/lib/mastery.ex: def build_quiz(fields) do Would make more sense if it looked like this: def build_quiz(fields) do | 2019-06-29 | I agree. Fixed. |
84 | SUGGEST | The second paragraph in the Prime Tests With Named Setups section begins with, “In version 1.3, Elixir released a describe block.” It would be clearer if it said something like, “In version 1.3 of Elixir the ExUnit.Case module added a describe block.” It’s a bit more explicit and lets the reader easily go and read about it in the docs if they want to. | 2019-04-30 | ||
24 | TYPO | In the last line of the last paragraph you say, “Let’s say you want to replace an item to a list”. It should be “Let’s say you want to replace an item in a list:” | 2019-05-18 | ||
30 | SUGGEST | “Strings Are Bitstrings” Isn’t it more accurate to say “Strings are Binarys”? Isn’t a binary called a bitstring when the total size of all the values isn’t a multiple of 8? | 2019-05-18 | ||
30 | SUGGEST | Section: “String Traps” I’ve tried searching the Erlang / BEAM online docs for references to this as I’d like to nail down when does a string become a “very long string”. Most helpful if a link is provided to the relevant Erlang docs. | 2019-06-29 | Anyone know where to find this documentation? If so I will add it | |
46 | TYPO | In the “Our Flow” aside, there is this sentence: “We made mistakes, refactored our | 2019-05-18 | ||
44 | TYPO | Correcting my previous report; I was looking at B1 still, but in B2 the typo is on page 44 not 46: “We made mistakes, refactored our data, refactored our functions and them made more mistakes.” Should be “then,” not “them.” In the “Our Flow” section at the top of the page. | 2019-05-18 | ||
144 | TYPO | starup should be startup ( shutdown and starup policies) | 2019-05-18 | ||
146 | ERROR | select_question/1 and pid/1 are not implemented so the example id broken. In the iex session: Mastery.select_question user1 (FunctionClauseError) no function clause matching in GenServer.whereis/1 The following arguments were given to GenServer.whereis/1: # 1 | 2019-06-29 | ||
39 | SUGGEST | Section: New Facts Don’t Invalidate Old Facts, 1st paragraph | 2019-06-29 | It's not strictly true that Erlang/Elixir processes have complete isolation. | |
48 | SUGGEST | Section Start With the Right Data, 4th paragraph: | 2019-05-18 | ||
55 | SUGGEST | Section “Edit to a Single Purpose”, Paragraph 6, Text: “Since struct! takes some fields as a KeywordDict , we’ll conform to that API.” I can’t find information on KeywordDict searching both Elixir & Erlang references. | 2019-05-18 | ||
77 | TYPO | 2nd paragraph, last sentence. | 2019-05-18 | ||
77 | TYPO | 3rd paragraph, last sentence. | 2019-05-18 | ||
77-78 | SUGGEST | Shouldn’t references to “Mastery.QuizBuilder” simply be “QuizBuilder” ? | 2019-05-18 | I think it's right. We're just showing the reduced ceremony. | |
78 | TYPO | Section “Provide Test Data With Fixtures”, Line: “Recall that our quizzes have the following structure:” The example defstruct is missing key/value: “last_response: nil” | 2019-05-18 | ||
9 | ERROR | In the paragraph starting with: “Here’s the magic.” there is a sentence “The state message simply sends a message back to the server.” | 2019-06-24 | ||
48 | DEFER | An object oriented veteran like me tries to picture a class diagram model showing the relationships between created data structures (or the ERD diagram if it was supposed to be the database design). I can follow the relationships based on the text but some kind of diagram maybe would help to see better what is going on and how the data will cooperate. | 2019-09-09 | We'll put it on the list and if there's time we'll do it. | |
88 | TYPO | It seems to me that the passage starting with “Keep in mind that this approach is not the only one that we could have chosen…” has been revised in the next couple of paragraphs, but the original version has accidentally been kept. | 2019-06-29 | ||
103 | TYPO | case expression is missing it’s input | 2019-06-29 | The input is piped in with the pipe operator (`|>`). | |
9 | SUGGEST | In general, I think it would be nice if the code aligned with what “mix format” would do by default; eg. diff —git a/lib/counter.ex b/lib/counter.ex def tick(pid) do Applies beyond this particular example, of course :) | 2019-06-19 | We're not going to fix that. Fixing each example individually is tough and running mix format reshapes the code in ways I am not willing to do. \n \nI know some will disagree, including some of our reviewers, but in my mind, it's ultimately a good call. | |
10 | ERROR | Macros for eg. GenServer are just used for injecting default callback implementations, avoiding some boilerplate, but the last paragraph states: “In Elixir, OTP uses the magic of macros to build all of this, the recursive loop, the message passing and more. It hides many of the messy details from you.” | 2019-06-24 | ||
88 | OK | Discussion of function eventually_match/2, paragraph 6. It appears you want to replace ‘answer’ with ‘number’. | 2019-06-29 | ||
26 | ERROR | Error in response So a User is actually a map with a struct field. Let’s look at the functions User | 2019-06-24 | ||
27 | SUGGEST | ````` Could clear some confusion by stating this needs to be defined in the module, otherwise you get: (ArgumentError) cannot invoke def/2 outside module | 2019-06-24 | ||
x | TYPO | In the first paragraph of the “Wildebeest Driven Design” section of “Introduction”, the first sentence: “James came up with…to remember the layers: Data, functions, tests, boundaries, layers, workers.” should be: “James came up with…to remember the layers: Data, functions, tests, boundaries, lifecycles, workers.” | 2019-06-24 | ||
118 | 113 | TYPO | The title “Test Drive the Quiz Manager” at the top of the page should be “Test Drive the Quiz Session”. | 2019-07-31 | |
146 | 141 | ERROR | In the paragraph after the select_question/1 and answer_question/2 function listing, first sentence, you state that these functions call pid(name) to look up process names. It should say that these functions call via(name). | 2019-07-31 | |
122 | ERROR | In the section about the boundary layer >> “Build the API layer” the validator for the Mastery.Examples.Math.build_quiz for the field :title fails because the validator is expecting a string whereas the example is using an atom. This is also reflected in the code example. | 2019-09-09 | Sorry, but I haven't been able to reproduce this in the final version of the book. | |
12 | OK | If you’re like us, you’ve found a valuable companion in Elixir, with some But to be honest this sentence doesn’t ring. | 2019-07-31 | ||
46 | DEFER | When comparing tuples with lists, the book uses the fact that you can use the “get_in” and “put_in” functions with lists as an advantage over tuples, because it makes writing and reading equally complex. However, you could also use those functions with tuples, you just have to switch from “Access.at” to “Access.elem” and the code works the same. It’s a small thing, but it may have a negative impact depending on the reader. PS.: I love your books and I’m really enjoying this one so far! Keep being awesome! | 2019-09-09 | This is a fair point and obviously correct, but we worry that asides like this detract from the main discussion. So, we hear you, but we're choosing not to go into the difference here. | |
7 | SUGGEST | “Recall that our public API had two functions…” Was this already mentioned somewhere? AFAICT there is no mention of the public API before this sentence. | 2019-07-31 | ||
34 | TYPO | first line of the second text block (first complete para on the page) …. leave Elixir is an SQL database. should be …. leave Elixir is a SQL database. | 2019-09-09 | ||
164 | ERROR | The start_quiz/2 function does not work as written as add_template is not defined in the Proctor module. I was able to get it to work with the following: defp start_quiz(quiz, now) do | 2019-09-09 | If you download our code, you'll see a helper function that does the forwarding. | |
46 | TYPO | In the field listing: name, atom, instruction, etc. | 2019-09-09 | ||
139 | TYPO | Erroneous backslash in iex console input, after …“name: TestSupervisor])”. Should remove backslash so that reader knows to hit enter and get the message from start_link. | 2019-09-09 | ||
148 | SUGGEST | The lookup function is: > def pid({_title, _email}=name) do … But we referred to the function in previous examples as via. One or the other isn’t quite right. | 2019-09-09 | via() creates the tuples needed to feed to GenServer functions, to access a process via the Registry. pid() is a different function for retrieving the PID directly. | |
200 | ERROR | I had this problem with my code so I got the source code from the pragprog.com zip file. After having run mix test in the root folder (mastery) in the BoundaryTests I get this ……………. Finished in 0.2 seconds Randomized with seed 685609 Then after cd-ing into the mastery_persistence folder running mix test results in failed tests as can be seen below. Opening a psql session on mastery_test database and running delete from responses solves this error. However, there should be a clean way to have the mix test command clean the database after the test run. 1) test an error in the function rolls back the save (MasteryPersistenceTest) . 2) test simple reporting (MasteryPersistenceTest) 3) test responses are recorded (MasteryPersistenceTest) Finished in 0.1 seconds Randomized with seed 384668 | 2019-09-09 | Sorry, but I haven't been able to recreate this. | |
164 | TYPO | > We process a handle_info where we basically take advantage of two functions we’ve already built, start_quizzes and reply_with_next_quiz_timeout. Function that’s used and called is build_reply_with_timeout not reply_with_next_quiz_timeout. | 2019-09-23 | ||
26 | ERROR | There is an error in the iex console (KeyError) key :STRUCT not found in: %User{email: nil, name: nil} Followed by the corrected command | 2019-09-23 | ||
147 | SUGGEST | It seems like some code is missing. This section should probably suggest updating the following functions in the Mastery module to def select_question(name) do def answer_question(name, answer) do | |||
166 | ERROR | Missing implementation of add_template in proctor.ex | |||
181 | TYPO | Bullet list under the heading “Integrate MasteryPersistence Into Mastery” - 2nd bullet 3rd word: “perstence” instead of “persistence” | |||
145 | ERROR | The description of restart option of child_spec is wrong, they are :permanent, :temporary and :transient, they got confused with the supervisor strategies (:one_for_one, :one_for_all, …) | |||
6 | SUGGEST | On page 6, the path mentioned /lib/counter/core.ex. But, this is not the same on a windows machine. After running mix new counter, we have a /counter/lib/counter.ex file. You may need to clarify the path for windows and unix-based OSs regarding the path. To get /counter/core.ex, it has to be created manually. The way it is written is as if this has been generated for you. | |||
7 | ERROR | In the Clock example, the print statement when running the program should start with: In the PDF B6 version, page 7 shows the print out starting with “The clock is ticking with 1”, but that can’t be the case since the run statement is run(f, 0) and the first call to your_hearts_desire is before the increment while count is initialized to 0. You guys should be testing your own code. | |||
111 | TYPO | In the Math module, the quiz_fields function return a title that is an atom. This makes the QuizValidator.validate_title on page 115 (PDF) fail since it validates the title to be a string when applied on page 124 (PDF) as: iex(3)> Mastery.build_quiz Math.quiz_fields (FunctionClauseError) no function clause matching in Mastery.Boundary.QuizValidator.validate_title/1 The following arguments were given to Mastery.Boundary.QuizValidator.validate_title/1: # 1 Attempted function clauses (showing 1 out of 1): def validate_title(title) when is_binary(title) (mastery) lib/mastery/boundary/quiz_validator.ex:12: Mastery.Boundary.QuizValidator.validate_title/1 | |||
122 | SUGGEST | The QuizManager have API-functions for build_quiz, add_template and lookup_quiz_by_title yet only lookup_quiz_by_title is used in the Mastery module. The others call GenServer.call directly. | |||
123 | SUGGEST | The QuizSession have API-functions for select_question and answer_question but they are not used by the Mastery module. Instead there are calls to GenServer.call directly. | |||
92 | SUGGEST | All the setup functions in chapter 5 merge in the values they set up in the context. This is not needed since ExUnit handles that for you. Do: Dont: | |||
149 | ERROR | If the Math quiz title is an atom the QuizValidator will fail. If it is a String the output would be different. iex(4)> title = Math.quiz.title | |||
90 | SUGGEST | Maybe it should be mentioned, that the downside of the stream method for random generators is, that without setting the test timeout explicitly or with using —trace, eventually_match/2 will run the full 60 seconds, before it fails, when no match is found. | |||
148 | TYPO | The printed Mastery module code does not reflect the archived code. The API implementation for answer_question/2 and select_question/1 calls the GenServer in QuizSession directly, whereas the function in the archive call the QuizSession API, as it is intended. When following the print version, this leads to exceptions, as we had to pass the session through Mastery.Boundary.QuizSession.via/1 | |||
167 | TYPO | “We will need to revise the QuizManager to return the active sessions for a quiz and also adapt QuizSession to end the sessions for a given title as our scheduler terminates them.” The QuizManager needs to be able to remove a quiz, not return active sessions (that is a job for the QuizSession) | |||
182 | ERROR | The mastery_persistence dependency in mastery’s mix.exs has incorrect path, it should be: {:mastery_persistence, path: “mastery_persistence”} | |||
189 | TYPO | We’d just replace the SessionServer with a SessionChannel, and that Channel module would accept the exact same messages, though we might not choose to wrap those handle calls in a public API. There is no module called SessionServer in Mastery, it’s called QuizSession (Mastery.Boundary.QuizSession) | |||
201 | ERROR | > Finally, we make sure the function in fact records responses with a simple This is not what the code does in the example. It reads the Response rows from the database and make sure it matches the response email from the setup. | |||
148 | ERROR | In “Touch Up the API Layer”, the select_question and answer_question functions do need to be modified. In both, the first argument to GenServer.call/3 need to be wrapped into a :via tuple: session —> QuizSession.via(session) | |||
166 | ERROR | The implementation of add_template used in start_quiz is missing from the book. def add_template(quiz, template_fields) do | |||
176 | ERROR | With Elixir 1.9.4, use Mix.Config is deprecated in favor of import Config. | |||
117 | TYPO | Int the Validator module, function “require” maybe missing the “d” letter because “require” is a macro in Elixir I suppose? Thank you for the book, it is amazing :) | |||
117 | ERROR | The check_field function returns a list of errors in all cases but one: | |||
329 | ERROR | When writing test for MasteryPersistance it’s needed to change the Sandbox mode to manual. Otherwise transaction will be committed and data leaked between tests. Adding Ecto.Adapters.SQL.Sandbox.mode(MasteryPersistance.Repo, :manual) to the test_helpers will solve this problem. | |||
28 | TYPO | The two function definitions at the top of the page seem to be invalid, as the function name is missing. | |||
60 | 60 | TYPO | I think in the first code snippet 2 and 3 lines should be indented 2 spaces | ||
60 | 60 | TYPO | 2 and 3 lines of first code snippet should be indented | ||
169 | ERROR | After working through the Chapter on Workers I ran into an issue where the code blows up with an ArgumentError. I thought I had merely made a mistake somewhere, but after pulling down the sample code and running it in code/Workers I encountered the exact same ArgumentError. The StackTrace is included: ❯ iex -S mix Compiling 14 files (.ex) 18:23:44.059 [info] Starting quiz simple_addition… 18:23:44.079 [error] GenServer Mastery.Boundary.Proctor terminating (ArgumentError) argument error (stdlib) gen.erl:169: :gen.do_call/4 (exit) exited in: GenServer.call(Mastery.Boundary.Proctor, {:schedule_quiz, , start_at: #DateTime<2020-03-08 02:20:05.597349Z>, templates: [[name: :single_digit_addition, category: :addition, instructions: “Add the numbers”, raw: “<%= | |||
211 | 206 | TYPO | In the description of the notify_stopped function the book states: > If there’s a pid, we send a tuple with the :stopping_quiz atom and But the code sample sends a :stopped atom. |