CHUCK:
Good morning!
LUKAS:
[sings] Ba da ba ba ba…
[Does your team need to master AngularJS? Oasis Digital offers Angular Boot Camp, a three-day, in-person workshop class for individuals or teams. Bring us to your site or send developers to ours -AngularBootCamp.com.]
CHUCK:
Hey, everybody. Welcome to Episode 20 of the Adventures in Angular podcast. This week on our panel, we have Lukas Reubbelke.
LUKAS:
Hello from West Side Phoenix.
CHUCK:
Aaron Frost.
AARON:
Hello!
CHUCK:
I'm Charles Max Wood from devchat.tv. Just want to give you a quick reminder to go check out JSRemoteConf.com. We're going to have an online conference in February, so should be able to make it. I hope you can make it. So go check it out. We also have a especial guest this week and that is Dan Wahlin.
DAN:
Hey, guys! Hello from the East Side of Phoenix.
CHUCK:
Do you wanna introduce yourself really quickly?
DAN:
Yeah, sure. So I live in Chandler, Arizona where it's a balmy 75F today, I think. we were just talking about that. Pretty nice.
CHUCK:
He has to keep rubbing it in.
DAN:
I know, I know. I just can’t shut up about it. I'm pretty happy with the winter. Talk to me about the summer and it's a different story, but pretty nice right now.
CHUCK:
I'm going to have to, just to get even.
DAN:
[Chuckles] But yeah, I run a software consulting and training company based in Chandler. And we do obviously a lot with AngularJS nowadays. In fact, I am currently on a project as we're speaking right now, that the Angular part is working, but the back end piece is not working. So, that's kind of what we do though, and yeah, I love the Angular stuff.
CHUCK:
Should have used Rails. Just sayin’.
DAN:
[Chuckles]
CHUCK:
I'm happy to help you with that if you need.
DAN:
All right. I'll get back to you on that.
CHUCK:
So today’s topic is structuring AngularJS project or structuring the code in an AngularJS project. I'm a little curious because I'm somewhat new to AngularJS in the sense that I haven't built like a gazillion projects with it yet. So most of the time, I just wind up putting, you know, my controllers all in one file each, and most of the other stuff in their own files and I just kind of split them up according to what they are, then it seems like it makes sense to me. Is there more to it than that? The framework kind of gives you a place to put stuff, so I'm wondering what is there beyond that we need to think about?
DAN:
This is the subject of many religious battles -- which I always laugh about -- because if you're using grunt or gulp -- which should be using to minify your scripts and concatenate them -- then ultimately, it doesn’t matter. So it all comes down to maintenance; what you or your team – if you are on a team – was doing. And it kind of have three approaches -- that I know Lukas and Aaron and John has a lot on this is as well out there -- but in the feature-based approach is what everyone preaches, which I like overall; the convention-based approach, which is to organize your files like you said. And I do like to put per file, typically and then concatenate them as appropriate with… I like gulp, personally.
CHUCK:
I think somebody just cried.
DAN:
[Chuckles] I won’t go into why I like Gulp better but anyway, the third is what I call a “blended approach,” and that's what I actually do. The feature-based approach I think is great if everybody on the team understands the features well, but if you ever have to hire contractors or get new hires on your team or you know people are switching around or whatever, I think that approach actually can be a little trickier than most people think about, if you're in the contracting world like I am -- or I know you are as well, Chuck -- because as you just don't know always who you're going to get.
And then, if there's no documentation – of course, everyone documents, I know but…
CHUCK:
[Chuckles] Of course.
LUKAS:
Sarcasm noted. [Laughter]
DAN:
There's no sarcasm there. Come on.
CHUCK:
I've taken over a few of those projects.
AARON:
The insincerity meter is off the charts, bro.
CHUCK:
Yeah, the documentation is “pick up the phone and call the last guy.”
DAN:
That's right. And if the last guy is not around, then you spend your time trying to figure out, “Oh, ‘people’, okay what's in the ‘people’?” And there's nothing wrong with that but what I like to do is mix the two. So I like to organize by…
CHUCK:
Can I back you up for a minute? What is the “feature organization” approach? So the one is the convention approach, and that's put all your controllers together, all your directives together, all of your modules together, blah, blah, blah, right? Your services together.
DAN:
So the other approach is to figure out what are the key major, high level features of your app and make folders for those. So if your app does something with invoices, you might have an “invoices” folder and you put your invoices views and invoices controllers, that stuff in there. Then you have another folder for purchase orders, maybe that's the feature of the app. I'm actually very much in favor of that approach. The only thing I don't like is somebody has to come up with those names. And if you do work in a scenario where your bringing on different contractors and things like that or new hires or whatever, the tricky part is does the name you thought made sense make sense to them for that feature? And most of the time, I think it does but what I like to do is kind of not only have the features, but also then I like convention. So I'm actually a big fan of convention. You probably are, Chuck. You mentioned some particular server side framework that actually has some nice conventions. And so I like to do what I call the “blended approach” where I'll mix... the high level features, I have my modules usually then I break it down into convention, then I break that into feature. So I go a little backwards than most people and most people laugh at me, and I just get my counseling and I'm okay with it.
CHUCK:
[Chuckles]
DAN:
So the typical way most people do it though is pure feature. And nothing wrong with that; I just like to do little more little more consistency, a little more convention mixed.
AARON:
So where I work, we do this feature folder stuff, but we also have a different approach for like certain stuff. Because there's certain pieces, certain directives, certain services the get used everywhere so it's tough to put them in a feature folder, right? Because they kind of belong to everyone. So we actually have like a common directory. And inside our common directory is all the stuff that’s going to be used everywhere. So if you're maintaining a file this in the common directory, you know, “Okay, this is used by everybody. I got to be more sensitive with this one than something that was just in my feature folder.” Does that make sense?
DAN:
Totally.
AARON:
That's the one exception to the feature folder that we have kind of embraced.
CHUCK:
One thing that I am wondering about though is so you have shared code and directives and services typically. You're not going to share a ton between the controllers per say or any model set up that you have, and your templates may or may not be shared. Do you ever find though that you have for example, on the single page app, you start working in invoices, so all the invoice stuff comes up but it a lot of times needs to reach into payment processing or some other feature? So, do you have the overlap and how do you deal with that?
DAN:
Me, personally, I do a lot along the lines of what Aaron said. If I have a single line of code that I think is going to be shared, then I'll move that out to a factory or a service – whatever is preferred there – and leverage it that way. But yeah, there's definitely some cases where you know it's not quite as cut and dry in the features -- this feature needs this feature needs this feature. And what I
try to do is abstract as much as I can out into reusable factory or service and that way it's not nearly as difficult to deal with.
AARON:
So I'm going to add to what Dan just said, because that's what we do. But kind of take that.. I'm going to use Chuck’s example he just put out there. We have this concept of rich data models, and so what we do for every type of model we get back from the server, we create a JavaScript class around it and then our services never return raw JSON; they return these instances of these classes. And so sometimes instead of putting that common functionality into a service or a factory like what Dan was saying, which we do, but sometimes we put it into the data models themselves so that if you're using the same data model in the invoicing screen as you are in the accounts payable screen, sometimes, you can extract the data into a rich data model into a JavaScript class rather than forcing it out into a service that gets injected to places.
CHUCK:
So what's the tradeoff between putting it into a model, versus putting it in to a service? Because it seems like they're probably good cases for each.
AARON:
That's the thing, you have to figure out what it is. The reason that we have totally embarrassed rich data models and putting a lot of logic into those, is because they are plain old JavaScript object. So we have a model system that is completely, it doesn’t care if we're using Angular 1.0 or 2.0 or React, like it doesn’t care, they are just JavaScript objects; they are not Angular cached objects or you know what I'm saying? So a lot of our code is just in raw JavaScript, it's not tied to a framework -- which in Angular land, who cares because we all do it in Angular, but it does give you some… like when we port to 2.0, we're expecting that that will make the port easier.
DAN:
I would agree. I think that's actually a nice way to abstract out, and you're kind of framework agnostic if you will.
LUKAS:
So speaking of abstractions -- I'll just chime in here real quick -- is that I’ve found that there's kind of a pretty good process in terms of… from going like very local from a controller to kind of this process of promoting your data, so that it becomes available to your application on a level that makes sense. So lot of times I may just start by putting the data or the functionality that I need right in the controller but then once I realize like, “Oh maybe a directive within my feature or maybe another controller within my feature needs that data, then I'll promote it to a service within just that feature.” But then from there you can say, “Oh, well, this other feature needs it.” Then from there you can just keep promoting it so that you can promote that into your common directory and then make it available. And I think even interesting enough is you could even then promote it to a rich model where it's just generic JavaScript, so that it gets…. now it's available, not only to Angular, but anything else that wants to consume it. And so there's just kind of this local to global kind of process that you can go through by just promoting it as you need it, without prematurely optimizing that data structure, that functionality before you actually need it somewhere else.
AARON:
I think that what Lukas described is exactly what I've seen. It kind grows into it. You don't know that you're going to have this insanely rich model, but then all of a sudden you realize it, so you promote it into that. You know what I'm saying?
DAN:
It's all refactoring. It's like doing a database; you start out with something then you realize, “I need this…” because, I don't know, maybe you didn’t know all the features up front – which is, that never happens, right?
LUKAS:
Yeah.
DAN:
So those type of things.
CHUCK:
So let me throw a scenario out there because it sounds like this is right along the lines of what we're talking about. Let's say for example that we have a podcasting site that hosts multiple podcasts. and I find that I'm making the same requests to the API and point five times when I load the page. So, should that be something that's moved out into a service?
DAN:
I do. Yeah. When it comes to things like business rules… and this isn't going to what Aaron said because that takes it to a whole nother level, but just talking pure kind of Angular. Did I say that right, by the way? Actually, I had somebody criticize how I say the word “Angular”. Apparently, I'm pronouncing it wrong.
AARON:
It's a little bit Phoenix-y for me, man.
DAN:
Is it Phoenix-y for you? Okay. I'll work on it.
CHUCK:
Yeah, it starts with an “A”, Dan.
LUKAS:
Not “Rangular”?
CHUCK:
[Chuckles]
DAN:
[Chuckles] I literally had somebody get a little upset at me. He's like, “You got to learn how to pronounce!” I'm like, “…Okay. Sorry, man.”
CHUCK:
Yeah. You're going to lose business.
LUKAS:
Did you just say “Angle-lar”? Because that's what I heard.
DAN:
“Angerer”, yes that's what I said. Anyway, when it comes to thinking it from a pure Angular perspective, I like to think in terms of reuse. And so yeah, Charles, I actually have what I call a data service... I did this for a long time before …Angular. Now I'm all conscious about it.
CHUCK:
[Chuckles]
DAN:
I did this a long time before and I used to have these little JavaScript objects that are just re-usable objects. It doesn’t matter if it was Java or Ruby or .NET or whatever – I’d do the same thing there. You build this little reusable objects and they just return promises… maybe tweak the data or something. But yeah, then you get tons of reuse. so I don't ever put my Ajax calls or anything like that in my controllers. I like to break all that out.
CHUCK:
That's really cool. I like that idea.
AARON:
When you read kind of the leading style guides, Chuck, like from John and from Todd, they have points where they say to do what Dan is saying, which is “Don't put http in your controller. Always abstract that out into a factory.” Because like for testability, there's a lot of reasons why… and they put on the style guides why you do that, but there's a lot of reasons why you don't do http straight into the controller.
CHUCK:
Yeah, makes sense. It just seems like the examples that you get into when you first get started, they put it there. And it's mostly a convenience thing, not because it's the right way to do it.
LUKAS:
Well, so let me jump in here. Going back to that process that I’ve talked about is I think sometimes developers can get paralyzed of like, “Oh, I've got this thing and I don't know what to do. Where do I start?” I don't think there's anything wrong with starting in the controller. Like a lot of times, I even just mock my data out. But when you understand how to promote that, then you follow that dictum of “make it work, make it right, then make it fast.” And so I would say once you understand the promotion process… it's fine start with the controller but ultimately, that's not where you're going to wanna end up on.
DAN:
I'll give you a real life example. So I have somebody just today, actually, there's a lady somewhere in the world who’s doing one of my Angular courses online and she has been going very deep [chuckles] into tweaking the samples I give and doing her own thing. And that's exactly what's been happening. She started with kind of putting everything in a controller then I'll say, “Well, that's good. You got it working. But now, consider this.” And I think once people, especially if they are newer with AngularJS, that they understand the role of factories and services… and even though the difference between those, that really changes everything because you can start of, like you said, Lukas, don't get paralyzed about it; just build something. I always laugh when people get all hung up of some of the stuff like the folders because it's like, “Do you really think my mom gives a crap [chuckles] when she hits your app?” We're the only ones that care from a maintenance stand point.
LUKAS:
Which brings up an interesting point is that I think that the requirement for a good file structure is the same as actually writing just good code -- is that it should be easy to maintain, easy to extend and it should be in a part, like self-documenting. So I find that my file structure actually matches my code structure internally. And I think that's the most important part is not being religious, per say, but finding something that is conducive to writing good code and facilitates that and being productive and maintaining your code, extending your code et cetera. So it's almost the requirements for a good structure is the same requirements for good code itself.
DAN:
Yeah. And you already mentioned -- I think Chuck mentioned it or Aaron, one of you guys -- for those listening that are maybe newer to this and you are feeling a little bit paralyzed: number one, do what Lukas said: don't be; number two, go check out John Papa’s style guide:
GitHub.com/johnpapa and you'll find it. There's a lot of stuff in there.
CHUCK:
We'll put a link in the show notes.
DAN:
And then Todd… I can’t say his last name,“Motto”? Is that right?
AARON:
Todd Motto. I call him Todd Motto.
LUKAS:
I call him “Tomato.”
DAN:
There you go. That works too. Anyway, he…
AARON:
He likes that one most.
DAN:
Does he?
LUKAS:
He told me.
DAN:
[Chuckles] There's some things that I read and those that I don't agree with every single thing, and that's the whole purpose of a style guide though is it just gives you some things to atleast consider. And the way I view it is I try to make all my code as dumb as possible. And what I mean by that is – this kind of ages me a little bit -- but you know back in the day, when we use to have like -- and I didn’t I work on these, just in case anybody brings it up, my age or something, I'm not that old – but anyone ever worked with like punched cards back in the day which…
LUKAS:
[unintelligible]
DAN:
Yeah. I never did. I honestly never did, but they used to have these mainframe terminals and they were really dumb. And that's how I like to think of it… “dumb” meaning that they relied on something else to actually get the data, and that's how I think of my controllers is I wanna make them as “dumb” as possible, at least in the end. Like, Lukas, you said, you know starting out maybe they aren’t quite so dumb if you will but in the long run, that's what I like to do this kind of make them very ignorant of where the business rules are or where the AJAX stuff is or whatever.
CHUCK:
It's so funny because I've had this conversation about Rails and about iOS, and so they haven’t have come up here. It's just funny. The idea of skinny controllers, where you put all of the logic somewhere else and the controller’s job is to basically get a request and coordinate the response.
DAN:
Yup. “Skinny controller” is probably a more politically correct way. “Dumb controller” probably won’t go over as well.
CHUCK:
Same idea, right?
DAN:
[Chuckles] Yeah. It's the exact same idea. I think it just makes it… you know, going back to that scenario, you asked, Chuck, about what if this feature x needs feature y or whatever, if you start hardcoding all that stuff in your controllers, then it's pretty hard to re-use that cross controllers versus if you start… what did you call it, Lukas? “Promoting” I think you called it.
LUKAS:
Yeah.
DAN:
You start promoting, now all of a sudden you get some reuse… and I see that my good buddy John Papa, you are…
LUKAS:
And he just had to move somewhere else. The guy is like the wind.
DAN:
So just like I said it, he had to move.
LUKAS:
John’s going to say something to me: “I need to move.”
DAN:
[Chuckles] Anyway, I really like what you said, Lukas, because when I first started frameworks, I get into that “paralysis by analysis” mode, because I just wanna do it right. I'm really anal that way and I want it to be right. And I think that's the wrong approach to take when you're new to this. I
would say learn what I call the “Lego blocks” first. Just build some out; like you said, prototype them and then you can start to promote and refactor. That's the whole fun of code as you write your tests and all that, you're going to be moving stuff around. If you're not, you're probably doing it wrong.
LUKAS:
+1.
JOHN:
So when you guys were talking about skinny controllers, one of the things I think about a lot is kind of the controller is the hub of the application, which is almost a misnomer because it's the brains of your app in Angular and it's the one that makes you think about, “Okay, how am I going to talk to the view? How am I going to talk to a factory or service? What do I plugin all of this other stuff inside of Angular?” But in the same sense, that makes it sound like it's really thick and heavy but it's not, right? It's skinny. It's really just the hub that connects all these things together. Is that how you look at it, Dan?
DAN:
Yeah. I look at the scope or your…. If you're doing controller as, your behind the scenes scope, if you will, as the…. it's the view’s model, which coming from some of the background John and I have done, we call it the view model. And it is literally just… it's the data for the view plus any interactions such as button clicks. The controller then knows how to fill that thing with data, but it doesn’t know these specifics I had to fill it, it knows how to depend on those other things like a factory or service or Aaron mentioned, these kind of rich data models even.
LUKAS:
I just see it as an air traffic controller, if you will, of the view, sends command to the controller like, “Hey, this thing happened.” Then controller will, if it involves kind of basically your data model or state within your data model, it will defer to a service which will perform that business logic and then send back a data model or a data object to the controller, so that the controller can then basically update the view. But it really is just very small, very specific and it's just kind of coordinating between the view and the rest of the app.
DAN:
I like that, “air traffic controller.” Yeah, it's a coordinator.
CHUCK:
I wanna change topics a little bit here and talk about views and templates because it seems like there are some views -- especially in single page apps -- where it almost basically replaces the entire page, and then there are others where it just replaces part of the page, and others where you have some directive that creates a widget off of a temple, and others that are re-used to make a list of things or to build table. How do you organize all of that stuff?
DAN:
What I like to do personally with views is where you put them in the folders, we've already kind of gone through the whole feature-convention blended whenever, I won’t go back into that, but I don't know that it matters as much for the views because… I have a Gulp task, ng-template, I think and it takes your templates and extracts some out and put some into a script, so you can just load them as a script. And that way, the client isn't having to go grab every single template from the server every time – not that that's bad, but I just think that you can pre-cache at least the common templates that you know people are probably going to hit. And then that could include the baby view ones. I call them the “baby views”. I think that's what you kind of mean. And you’re talking about where you replace parts of a page, right? Parts of a view?
CHUCK:
Yeah.
DAN:
Yeah. So in AngularJS out of the box, I think that's where the new routers are going to help a lot and that's why a lot of people use UI router. But ng-include works really well of course for loading the what I call “baby views” – a view within a view – but of course, the built in router as of today, which we'll hopefully be changing soon, but as of today, it doesn't have a great way to load a view in a view. And that's where you get into, like I said, UI router and states and you can kind of have routes within routes if you will and that's where the new router, which word on the street, is still being back ported to 1.3 or whatever the next version will be will I think offer a lot of value. Because probably if I have to pick on Angular on what don't I like, there's a few things but I mean overall I love it, but that's one of the number of things I don't like is the router compared to some the others out there – Ember’s or Durandal’s even – is not quite powerful enough when it comes to loading those little baby views. And you can work around it, but what people end up doing if you use the native router – and you guys can chime in here -- is the load of view, which is really just a wrapper around those what I’ll call “baby views” which is not nearly as efficient as it would be if you could just reload a little kind of portion of the overall view.
JOHN:
Dan, one of the things I get in discussions a lot lately is about let’s say you’ve got a view and could that view be done to an ng-include? It could be done to a UI view or an ng-view? It could also be done as inline code as an if, as a switch, or you can just make the whole thing a directive. So in that latter, the ones I've been hearing more lately where everything becomes a directive. And I feel good about that, but I also feel that could also be a horrible pitfall because you're going to end up with like directives that refer to directives, that refer the directives that refer to… you get the idea. [Laughter]
DAN:
A DDO of a DDO of a DDO.
JOHN:
Yeah! How do you maintain that kind of a thing when you’ve got… you know, it reminds me of the days we had [?] , we had seven levels of object inheritance and it was like, “How do you debug this thing?” But I can see the attraction to it as well. What have you seen out there that works and what doesn't work?
CHUCK:
Can I ask real quick how many layers do you get before it's an indirection or an indirective?
[Laughter]
DAN; Nice!
LUKAS:
[mimics sad trombone sound]
DAN:
You guys have sound effects on the show?
CHUCK:
Nope. [Chuckles]
JOHN:
No. It's really just Lukas. Lukas is our sound effect. [Chuckles]
DAN:
[Laughs] Yeah. So first off, and John knows this of me very well because we talk fairly often. I'm not a [?] at all. I'm one of those spirit of the [?] guys. So my general take is use what works best for your team. I mentioned this earlier. I just get a good laugh out of these people that, “If you're not doing it this way, it's wrong!” It's like, “Who the heck said that was the only way, man?” Because there is just too many ways. Now, yeah, there are some best practices of course, but when it comes to what you asked about, I personally, I'm totally fine with ng-include if it's just loading a view such as maybe a header portion or footer portion or a re-usable list of items or something to use across multiple views, just use an ng-include, I mean, that's what it's for and it works pretty dang well in most cases. But if you need more flexibility and you’ve got to tweak the data comes in and out of that or whatever, then I could totally see the attraction to maybe even a re-usable directive, kind of like ng-include, right? But your own that has some little tweaks that you need over and over and over. And so my thing is hey, I find myself needing to make these tweaks over and over and over, then yeah, I probably would look at a directive or something like that, but if I'm just loading a view it's like, why go to the trouble of having that wrapper around your view when you could just use the built in directive, ng-include.
JOHN:
I kind of agree with you there. What I've usually done is I usually start with ng-include for static type of linking like footer, header, sidebar and stuff like that. And then if it becomes more reusable, I wrap it into a directive. But the main view itself, what I call “the content area”, I usually start out with just making it a view -- whether it's UI view or ng view -- and then I drop in directives on that, but I've hesitated from taking the view itself in making its own directive. So that's kind of where I usually draw the line personally, but I'm with you. Whatever works for your team is key. I think consistency in a team is really, really important. Not always doing it the perfect way, but doing it in the way that other fifty people you're working with are doing it.
CHUCK:
Which is the way to John does it.
LUKAS:
That's what he tells me, at least.
AARON:
So I totally agree with what John just said. I think the “everything is a controller movement” is different than this. I think that “everything is a controller” is kind of everyone realizing, “Oh, scope inheritance isn't good. Like, it's not awesome, so if I make everything a directive with it's own isolated scope, then we can kind of stop people putting a method on a parent controller and using it two controllers deeper. Because for me, that's a huge anti pattern. And so I think that “everything is a directive” idea is more to prevent that kind of rubbish than it is to say… to enable like when we'll load stuff. But that's my take.
JOHN:
I agree with you totally, Aaron. And I think I'm really trying to put myself in the shoes of people who do that directive inside of directive, that Russian stacking dolls syndrome, and what I think sometimes people get into that for is if you do that route, first of all, it helps you reuse code. That's a great advantage of it. But if you come from other environments where everything became a component like user controls inside of user controls, that's kind of the same methodology. The problem I end up seeing with it though is maintaining it. For example, I recently got something that had seven layers of directives in it and I call it “the seven directives of hell” and one of my teammates was like, “Really? That sounds bad!” [Chuckles]
DAN:
It is bad. [Chuckles]
JOHN:
I was trying to explain how it worked and I partially wrote it and I couldn’t even explain how it worked to somebody, so that's why I started realizing maybe I over architected this a little. But I’d like to hear the other side of it. Does anybody here do that? I don't wanna say it's a bad thing, because I don't truly understand what the huge pros of it are, either.
LUKAS:
Well, if I could propose an alternate solution to this that I've had good luck with is when you have kind of this complex, visual hierarchy, instead of actually turning it into a bunch of directives, because I definitely think there’s a place for that is, is it a component? Are we going to re-use it in other places? Which is you can really run into some problems with these nested, kind of “directive dolls” if you will, is that another way to handle this is with UI router and treating it as a state machine. And especially with their named views, it allows you to provide very granular and specific control over parts of the page, and then you treat it as instead of this composition of directives, rather as a state machine that I'm in this state, and these are the views that I want to use; these where I want them to be and then you can as well control what data gets resolved into those views based on some kind of state. And really do some a really elegant things within your view and you're not having to use directives to kind of accomplish the same thing.
JOHN:
I think maybe we have a topic for a future show. [Chuckles]
LUKAS:
I think we do. It's pretty fascinating.
DAN:
Yeah, that one could go a lot deeper, for sure.
JOHN:
It could and I think even discussing UI router and ng-router and then the new proposed router, it should be something we should get into a little bit deeper as well.
DAN:
Yeah, my thing on all this is keep it simple. And it doesn't mean it won’t get hard by keeping it simple, but when I first came out of college and started one of my first jobs, I built an app that I was so proud of. It was actually pretty complex, like you said, John, it's one of those you look at that I wrote it and I couldn't even really figure out what it was doing anymore. And I'll never forget, we went down in production -- and this is back in the 90s, so it was a long time ago but back then, logging and all that was still… nobody have heard of it. [chuckles] We did, but not very well – and it was like a needle in a haystack trying to debug this stupid thing. So ever since then, I always take the, “Hey, what's the easiest way we can do this, but still the most flexible way?” Doesn’t mean like we were talking about use ng-include for everything. It doesn’t mean use a UI-router for everything. It means find the proper balance. And I think, every team as you said John, needs to sit down and have a discussion on what works best for us for whether it's folders or laying out the files or doing what we just talked about or whatever it is.
JOHN:
Exactly. And I think that's why probably the best tip is to for your team, sit down and do this and create your team’s style guide. Your team has to have your own one that you guys all live with, whether it's a five-person team or hundred-person team.
DAN:
Absolutely.
CHUCK:
Yeah. Makes sense. Anything else that we missed? Not covered? Before we get into the picks.
DAN:
Well, since it was on the topic of generally structuring Angular applications and things like that, I've already mentioned John’s style guide and if you haven't checked that out -- everyone out there listening – you definitely need to or Todd's as well. There's tons of good, like, “why this is better than this,” and for the teams, that might be sitting down to take the time to make their own little style guide, that would be a great way to actually get a really solid foundation. You may not agree with everything. There's about 90% of what John wrote that I'm like, “What's he talking about?” No, I'm just kidding.
CHUCK:
[Chuckles]
But there's some stuff in there that I totally agree with, and there's some stuff I tweak a little bit – and I think everybody does that -- but if you don't take the time to read through it, I guarantee – especially if you're new to this -- you'll never even have thought of a particular scenario on why you should do it. For instance, if you’ve been doing JavaScript a long time, it's pretty natural to do, immediately invoked function expressions and all that type of stuff, but if you haven’t, you might not even thought of doing that and that's one of the things John covers in the style guide, it's jpapa.me/ngstyles is the easiest way to get there. And anyway, he'll walk through a lot of the different things you can do. And I again as a team would sit down – just like he would, with really any language – say, “Hey, here’s how we're going to structure our modules. Here’s how we're going to structure our controllers and our factories, and here's where the reusable ones go. And figure out the folder thing.”
And it's going to take some discussions and I guarantee there's probably going to be some arguments because developers, luckily, were not opinionated at all, so everybody will just agree, right? But in reality, once you get done, you're going to have a nice foundation. And now if you do what I mentioned earlier, have to hire whether it's contractors or new hires or if somebody goes on vacation or whatever it is and you got to step in and fix it, you should now, not walk in to somebody else’s app and go, “What the? What is this?” You should walk in and go, “Okay, that looks like mine,” If you're on the same team, anyway.
CHUCK:
All right. Very cool. Let’s go ahead and get to the picks. Aaron, do you wanna start us off with picks?
AARON:
Yeah. I'm going to do a pick real quick. It's anyone who's not opening their store on Thanksgiving.
CHUCK:
[Chuckles]
AARON:
I guess I'm kind of a nerd and don't pay attention to regular news, because I saw this commercial where Scheels was like, “Hey, just so you guys know, we're not opening on Thanksgiving. We want you and our employees to spend Thanksgiving with their families.” And I was like, “I'm buying Christmas gifts as Scheels this year because I think that's a really cool stance to take.”
DAN:
Nice. I agree.
AARON:
So anyone who does that, I'm picking you.
CHUCK:
Yeah. My wife’s a Black Friday nut, and yeah, so she has plans Thursday night.
DAN:
You better grab the credit card before she goes out and hide it or something.
CHUCK:
Oh, it's too late. I think she's already cashed out stuff.
[Chuckles]
CHUCK:
Lukas, what's your pick?
LUKAS:
So my pick is if you're in Phoenix on December 13th, come to an event that I am putting together: HolidayJS. So you can go to HolidayJS.com. It's a free event, so it's like an Oprah Christmas special for programmers. It's going to be super awesome – food, hacking, prizes – everything.
CHUCK:
Very cool. I forgot to ask you guys for tips. Do you guys have tips you wanna share? Aaron and Lukas?
LUKAS:
UI router is awesome. Learn it, love it, use it.
CHUCK:
All right. John, do you have some picks for us?
JOHN:
Yeah, sure. So my tip, I'm going to do first for Angular. It's really an anti-tip. I'm going to borrow something Aaron said, which I firmly agree with and that's when you're creating directives, I think the de facto if you don't wanna think about is go ahead and create isolated scopes. So the anti-tip is by avoiding isolated scopes, you're kind of coupling yourself to whatever the outer container is. So, my tip is consider using an isolated scope in your directives if you're not already. And then my pick is going to be, and I'll put a link in here for everybody, it's using Grunt and Bower and npm and all that stuff right from Visual Studio 2015. There's some pretty cool stuff that they’ve added to it. And not a lot of folks know, but Visual Studio now has a new free edition called Community. I think it’s what its called. Is that right, Dan?
DAN:
I think so. Visual Studio Community, yeah.
JOHN:
So now you can get all the power of Visual Studio and it's not like a crippled version; it's the full pro version, basically, the old one called pro and it's called Community. You get it for free and you can do grunt, bower, npm – all these cool stuff right inside Visual Studio.
DAN:
Yeah. Even if you're not a Visual Studio fan – I am, I like a lot of editors, actually not just one – it's impressive. It's all visual and you can actually see your tasks visually. It's pretty neat. I've been playing with that as well, so pretty cool stuff.
CHUCK:
All right. I think I got plenty of tips out of the show, so I'm not going to share any there. I do have a pick and it's another podcast called Life on Fire by Nick Unsworth. It’s pretty darn good. He has video versions and it's a lot about marketing and things like that. So you can go and check that out.
I think it's just lifeonfire.com. Dan, do you have a pick and a tip for us?
So my tip – Lukas will laugh at this one – is don't depend on a tool like Outlook to cancel meetings.
LUKAS:
[Chuckles]
DAN:
Because apparently, some of those cancellations don't actually make it to the person that you're trying to cancel on. So I've had that happened twice, actually lately where everybody is like, “Hey, I'm here.” And I'm like, “Whoa. I canceled.” “No, I never go it.” So that's my tip is always, always, always make sure that you send a separate email when you cancel a meeting because two meetings, I've had this happen the last two weeks. My pick is probably going to too late because it's the Black Friday thing. So I'm pretty psyched. I have a new I Mac coming – the 4K – and I needed a new copy of Parallels because I still run that for the Windows side, and they have a deal going right now for the Black Friday thing, which like I said, by the time the podcast gets out it maybe be too late, but you get like Camtasia, and a password manager. It's like $300 worth of software for the price of the… or the Parallel’s license, which is like $80. So anyway, I was pretty excited about that, so I of course, had to waste the money and order. You did that deal too, Lukas, I
see? [Chuckles]
LUKAS:
Yeah, it's great.
DAN:
It's a good deal. So if it's still around up through the holiday break, then it's a good deal.
CHUCK:
Aaron, are there any announcements or news about ng-conf that you wanna share?
AARON:
Yeah, I'll just kind of update everyone on the status of the ticket sales because there's a lot of people wondering what's up. So last year, we did three rounds of ticket sales and this year we only did two. So a lot of people are expecting that we have more tickets to sell and they're hoping that they are going to be able to come. And I just wanted to share the bad news that we don't have more tickets to sell. The ticket sales were crazy. The first round, we’ve crashed Tito. I don't know if you guys saw that, but Tito had never seen that much traffic before at one time. And so they worked on their servers and got it ready for round two and then round two went smoother – it went mostly smooth – a couple of people still had issues, but it was mostly smooth. But the tickets effectively sold out in like one second because as soon as the button was available, we had 25,000 people trying to buy a handful, like, way less than that tickets.
DAN:
You need to get on tour, Aaron.
AARON:
I know.
DAN:
Like some of these bands opening it up for concerts.
AARON:
I know. I talked to Igor and their team can only do two conferences a year and so, getting a tour of ng-conf is tough because the big draw is that everyone wants to see the Angular guys. The only other option would be putting together like the biggest names in the Angular community and doing a conference without the Angular team -- or maybe just one or two of them. I don't know. But yeah, so that's kind of where that's at. It's going to be an insane event. Though I wanted to let everyone know, we're working on a program called ng-conf extended, where we want people to sign up to like host remote viewing parties, and we'll work with you to make t-shirts and some sort of like small treats available to the people who come to your event. And we also will work with few of you to get like a web camera, so that you guys can ask questions live at the Q&A at the panel at the end of the conference. So, stay tuned for news on ng-conf extended because we're going to need some extended organizers all over the globe. We’ve already got some guys in Brazil and Mexico wanting to host, so if you wanna host, tweet at the ng conf account on Twitter or tweet me. I'm @js_dev on Twitter, so tweet me on there. We'll make sure you guy get set up as organizers. But cool news: Dan and John Papa and Lukas, they are actually all speaking at the event, so it's going to be really cool.
DAN:
Yeah. I'm excited. It was awesome last year, so for those that didn’t get tickets, definitely watch all the stuff Aaron’s talking about because I'm telling you, I would have to say it's the coolest conference I've been to in the last like ten years, probably.
LUKAS:
True story, bro.
DAN:
Yeah. They did a really good job.
AARON:
This year is going to be even better. I mean, I'm not trying to brag but the planning we're putting into it is pretty awesome. It's going to be cool.
CHUCK:
Awesome. Well, if there's nothing else, then we'll go ahead and wrap up. Thanks for coming, Dan.
DAN:
Yeah, thanks for having me!
CHUCK:
We'll end the show. We'll catch you all next week!
[This episode is sponsored by Mad Glory. You’ve been building software for a long time and sometimes it gets a little overwhelming; work piles up, hiring sucks, and it's hard to get projects out the door. Check out Mad Glory. They are a small shop with experience shipping big products. They're smart, dedicated, will augment your team, and work as hard as you do. Find them online at madglory.com or on Twitter at @madglory.]
[Hosting and bandwidth provided by The Blue Box Group. Check them out at bluebox.net]
[Bandwidth for this segment is provided by Cache Fly, the world’s fastest CDN. Deliver your content fast with Cache Fly. Visit cachefly.com to learn more.]
[Do you wanna have conversations with the Adventures in Angular crew and their guests? Do you wanna support the show? Now you can. Go to adventuresinangular.com/forum and sign up today!]