1 00:00:04,960 --> 00:00:19,999 [Music] 2 00:00:20,680 --> 00:00:26,240 but before that we have Sam Sam is a 3 00:00:24,199 --> 00:00:28,080 professional software developer amateur 4 00:00:26,240 --> 00:00:31,720 rocket scientist and 5 00:00:28,080 --> 00:00:33,320 astronomer they love python Jango cats 6 00:00:31,720 --> 00:00:35,680 working on their personal software and 7 00:00:33,320 --> 00:00:37,800 Hardware projects everything space 8 00:00:35,680 --> 00:00:41,960 playing games of all kinds and tinkering 9 00:00:37,800 --> 00:00:41,960 with 3D printers please welcome 10 00:00:45,960 --> 00:00:49,840 Sam so yeah this is a bit of a 11 00:00:48,160 --> 00:00:52,800 postmortem so it's going to be 12 00:00:49,840 --> 00:00:52,800 interesting 13 00:00:53,600 --> 00:00:58,920 um so yeah I'm Sam uh I'm a freelance 14 00:00:57,239 --> 00:01:00,399 software developer and consultant uh 15 00:00:58,920 --> 00:01:02,359 I've been working on some space robots s 16 00:01:00,399 --> 00:01:04,559 a startup and recently started a podcast 17 00:01:02,359 --> 00:01:06,640 as well uh the rest of the contact info 18 00:01:04,559 --> 00:01:07,840 is on the slide just you know wasting 19 00:01:06,640 --> 00:01:09,680 time so anyone who wants to take a photo 20 00:01:07,840 --> 00:01:13,280 of it has a chance but it'll be there 21 00:01:09,680 --> 00:01:14,400 later so to do a postm modov project we 22 00:01:13,280 --> 00:01:16,200 kind of have to start with what the 23 00:01:14,400 --> 00:01:19,200 point of the project was what was the 24 00:01:16,200 --> 00:01:21,520 aim and in this particular case it was 25 00:01:19,200 --> 00:01:23,720 just a simple project it was a regular 26 00:01:21,520 --> 00:01:25,680 run-of-the-mill business SAS for a very 27 00:01:23,720 --> 00:01:27,960 specific business vertical nothing 28 00:01:25,680 --> 00:01:29,280 complicated no plans to become a unicorn 29 00:01:27,960 --> 00:01:32,479 and change the world and become 30 00:01:29,280 --> 00:01:34,560 billionaires just regular business and 31 00:01:32,479 --> 00:01:37,000 it was going to be done with MJS and D 32 00:01:34,560 --> 00:01:38,880 Jango with Django rest framework now for 33 00:01:37,000 --> 00:01:40,200 anyone who's not familiar with MJS it 34 00:01:38,880 --> 00:01:42,200 has a number of really beneficial 35 00:01:40,200 --> 00:01:44,159 features for this kind of plug andplay 36 00:01:42,200 --> 00:01:45,560 functionality uh in the fact that it 37 00:01:44,159 --> 00:01:48,680 actually can base everything off the 38 00:01:45,560 --> 00:01:50,280 Json API and you can get a nice just 39 00:01:48,680 --> 00:01:52,840 plug andplay kind of functionality from 40 00:01:50,280 --> 00:01:54,360 it and other than just the usual man of 41 00:01:52,840 --> 00:01:55,759 business logic getting put in the back 42 00:01:54,360 --> 00:01:58,039 end and the front end where it needed to 43 00:01:55,759 --> 00:02:01,079 be this was just straight up a 44 00:01:58,039 --> 00:02:04,960 JavaScript Spar and a Json API back end 45 00:02:01,079 --> 00:02:07,880 nothing fancy and that's where you start 46 00:02:04,960 --> 00:02:09,160 from your basic concept digging in how 47 00:02:07,880 --> 00:02:10,759 you actually going to put it together 48 00:02:09,160 --> 00:02:12,400 well for starting point there was some 49 00:02:10,759 --> 00:02:14,040 thirdparty app compatibility that was 50 00:02:12,400 --> 00:02:16,000 going to be used we had the Django rest 51 00:02:14,040 --> 00:02:17,560 framework we had Jango polymorphism 52 00:02:16,000 --> 00:02:19,200 because when we did the model and schema 53 00:02:17,560 --> 00:02:20,680 work we realized we had some 54 00:02:19,200 --> 00:02:22,400 polymorphism that we needed to account 55 00:02:20,680 --> 00:02:24,200 for and there were a few other minor 56 00:02:22,400 --> 00:02:26,400 libraries along the way that you know we 57 00:02:24,200 --> 00:02:27,920 all necessary parts of making an entire 58 00:02:26,400 --> 00:02:30,239 Django app if you aren't going to sit 59 00:02:27,920 --> 00:02:32,280 there and write it all from scratch half 60 00:02:30,239 --> 00:02:35,360 the benefit of using a framework is the 61 00:02:32,280 --> 00:02:37,680 ecosystem now I mentioned that it's 62 00:02:35,360 --> 00:02:39,599 compatibility well that's because a big 63 00:02:37,680 --> 00:02:43,560 chunk of this was decided to be built as 64 00:02:39,599 --> 00:02:47,959 a reusable app now it does make sense 65 00:02:43,560 --> 00:02:50,640 why but it it has consequences 66 00:02:47,959 --> 00:02:51,840 now it's a multi-tenant app since it's a 67 00:02:50,640 --> 00:02:54,400 SAS there are going to be multiple 68 00:02:51,840 --> 00:02:57,800 customers so each one is going to need 69 00:02:54,400 --> 00:02:58,680 to have their data kept separate now 70 00:02:57,800 --> 00:03:00,120 there's going to be background 71 00:02:58,680 --> 00:03:02,040 processing there's going to be the usual 72 00:03:00,120 --> 00:03:04,720 celery for background jobs there might 73 00:03:02,040 --> 00:03:06,400 be some occasional Chron jobs nothing 74 00:03:04,720 --> 00:03:09,040 fancy just straightforward good 75 00:03:06,400 --> 00:03:11,840 oldfashioned business logic 76 00:03:09,040 --> 00:03:13,920 stuff now I mentioned the multi tency 77 00:03:11,840 --> 00:03:15,840 and I mentioned building it as a 78 00:03:13,920 --> 00:03:18,920 reusable app this is what makes the 79 00:03:15,840 --> 00:03:20,480 drive on this because when you dig into 80 00:03:18,920 --> 00:03:22,760 the actual process and when the 81 00:03:20,480 --> 00:03:26,120 customers use cases were explained what 82 00:03:22,760 --> 00:03:27,720 we noticed was okay there is a overlap 83 00:03:26,120 --> 00:03:30,400 between the customers so some of the 84 00:03:27,720 --> 00:03:32,760 customers have multiple location and 85 00:03:30,400 --> 00:03:34,799 those multiple locations need to have 86 00:03:32,760 --> 00:03:35,879 commonality things can be moved from one 87 00:03:34,799 --> 00:03:38,720 to the other some of the things are 88 00:03:35,879 --> 00:03:41,439 shared between them but only some of 89 00:03:38,720 --> 00:03:43,439 them have that so there's a mix between 90 00:03:41,439 --> 00:03:46,239 single operators and multiple operators 91 00:03:43,439 --> 00:03:47,879 and groups of operators and it needs to 92 00:03:46,239 --> 00:03:50,640 be able to handle all of this in order 93 00:03:47,879 --> 00:03:53,000 to be useful for the actual customer 94 00:03:50,640 --> 00:03:55,200 base and that's where it gets 95 00:03:53,000 --> 00:03:57,599 complicated and it becomes a plan to 96 00:03:55,200 --> 00:03:59,840 make that tency information that 97 00:03:57,599 --> 00:04:02,400 management of the multi-tenancy into 98 00:03:59,840 --> 00:04:02,400 reusable 99 00:04:02,680 --> 00:04:06,799 piece how hard can it 100 00:04:05,239 --> 00:04:09,239 be 101 00:04:06,799 --> 00:04:11,200 and this is the part where I have to put 102 00:04:09,239 --> 00:04:14,599 out a carat the code you were about to 103 00:04:11,200 --> 00:04:16,639 see is old unmaintained not free but it 104 00:04:14,599 --> 00:04:18,440 is open source and feel free to ask a 105 00:04:16,639 --> 00:04:20,479 question about that later if you want 106 00:04:18,440 --> 00:04:22,320 and I going to do the horrible thing of 107 00:04:20,479 --> 00:04:24,199 confronting code that I wrote over half 108 00:04:22,320 --> 00:04:26,960 a decade 109 00:04:24,199 --> 00:04:29,560 ago because nothing is quite so humbling 110 00:04:26,960 --> 00:04:31,840 as realizing how stupid you used to be 111 00:04:29,560 --> 00:04:34,280 and and I've left it in wats and all 112 00:04:31,840 --> 00:04:36,680 there are todos there are comments it's 113 00:04:34,280 --> 00:04:39,320 it's got all of it so we get to the 114 00:04:36,680 --> 00:04:41,199 implementation part we start off with a 115 00:04:39,320 --> 00:04:42,880 fairly straightforward reusable app I'm 116 00:04:41,199 --> 00:04:45,840 just going to make a poetry project 117 00:04:42,880 --> 00:04:46,919 great off we go real easy then we get to 118 00:04:45,840 --> 00:04:48,880 the basic models after you do your 119 00:04:46,919 --> 00:04:50,440 Django scaffolding don't think anyone 120 00:04:48,880 --> 00:04:53,039 needs to see eight Django commands at 121 00:04:50,440 --> 00:04:54,880 this point so we've got a tenant model 122 00:04:53,039 --> 00:04:56,960 you can't really track tencies without 123 00:04:54,880 --> 00:04:59,080 having a tenant it's straightforward 124 00:04:56,960 --> 00:05:01,280 model we've got a name we've got an ID 125 00:04:59,080 --> 00:05:03,199 we've got a slug for short URL stuff and 126 00:05:01,280 --> 00:05:05,080 we've got some Json fields to keep track 127 00:05:03,199 --> 00:05:08,440 of various bits of metadata that don't 128 00:05:05,080 --> 00:05:11,240 really have a plan yet because like any 129 00:05:08,440 --> 00:05:14,560 business SAS requirements may change you 130 00:05:11,240 --> 00:05:16,320 need to be a bit more flexible and with 131 00:05:14,560 --> 00:05:17,400 that we've then got the relationships 132 00:05:16,320 --> 00:05:19,319 because obviously if we're going to 133 00:05:17,400 --> 00:05:21,319 match users to tencies we need to 134 00:05:19,319 --> 00:05:23,600 actually track that relationship so 135 00:05:21,319 --> 00:05:26,039 there is a tenant relationship piece 136 00:05:23,600 --> 00:05:27,800 here which is using one of the mixins 137 00:05:26,039 --> 00:05:29,880 you'll see soon and it's tracking the 138 00:05:27,800 --> 00:05:32,000 permissions so it's got the permission 139 00:05:29,880 --> 00:05:33,400 attached to these objects and that lets 140 00:05:32,000 --> 00:05:35,120 us work out whether someone is allowed 141 00:05:33,400 --> 00:05:38,759 to see things inside of a tendency or 142 00:05:35,120 --> 00:05:40,160 not and then we've got a model manager 143 00:05:38,759 --> 00:05:42,560 because at the heart of this kind of 144 00:05:40,160 --> 00:05:44,400 multi- tendency is keeping track of 145 00:05:42,560 --> 00:05:46,800 which kinds of data should come out of 146 00:05:44,400 --> 00:05:49,039 the big everything in the same pile 147 00:05:46,800 --> 00:05:50,840 schema other kinds of multi- tendency 148 00:05:49,039 --> 00:05:52,600 let you just put separate databases and 149 00:05:50,840 --> 00:05:53,840 keep things separate that way that 150 00:05:52,600 --> 00:05:55,440 wasn't going to be practical here 151 00:05:53,840 --> 00:05:59,120 because of the way things needed to be 152 00:05:55,440 --> 00:06:01,400 moved between on a regular basis so the 153 00:05:59,120 --> 00:06:03,400 plan was keep it all in the one schema 154 00:06:01,400 --> 00:06:05,639 and the only way to work with that is to 155 00:06:03,400 --> 00:06:07,479 do your SQL queries the right way so we 156 00:06:05,639 --> 00:06:09,400 have our query sets and in this case 157 00:06:07,479 --> 00:06:12,720 you'll notice that at the top here it's 158 00:06:09,400 --> 00:06:14,479 actually doing a return none so if we're 159 00:06:12,720 --> 00:06:18,440 not actually getting a tenant it returns 160 00:06:14,479 --> 00:06:22,039 none because it shouldn't actually give 161 00:06:18,440 --> 00:06:24,160 information when there's no tency there 162 00:06:22,039 --> 00:06:28,080 so the default query path when this is 163 00:06:24,160 --> 00:06:30,080 invoked will filter for a tenant and 164 00:06:28,080 --> 00:06:32,360 this is what we use inside of the ACT 165 00:06:30,080 --> 00:06:34,160 base model after we get through the 166 00:06:32,360 --> 00:06:37,120 other one because there's a multi-tenant 167 00:06:34,160 --> 00:06:38,759 one as well and the only difference here 168 00:06:37,120 --> 00:06:40,800 is that because there's a many to many 169 00:06:38,759 --> 00:06:43,360 for these models the query is slightly 170 00:06:40,800 --> 00:06:45,680 different and when we use them inside 171 00:06:43,360 --> 00:06:47,080 the models it is very much what you'd 172 00:06:45,680 --> 00:06:49,840 think it's just a straightforward 173 00:06:47,080 --> 00:06:51,599 abstract based model mix in and it's 174 00:06:49,840 --> 00:06:53,639 using the single tenant model manager 175 00:06:51,599 --> 00:06:57,360 there the multi-tenant one uses the 176 00:06:53,639 --> 00:06:58,440 multi-tenant model mix in and it 177 00:06:57,360 --> 00:07:00,160 obviously has to keep track of the 178 00:06:58,440 --> 00:07:02,800 original manager because every now and 179 00:07:00,160 --> 00:07:04,680 then you need your Escape patch but by 180 00:07:02,800 --> 00:07:07,599 default you want it to be doing things 181 00:07:04,680 --> 00:07:09,000 the way you plan on it doing them and 182 00:07:07,599 --> 00:07:10,520 there's a bit of a save logic down there 183 00:07:09,000 --> 00:07:11,759 because obviously you don't want to save 184 00:07:10,520 --> 00:07:13,360 something that belongs to a tenant 185 00:07:11,759 --> 00:07:15,960 without actually having a tenant to save 186 00:07:13,360 --> 00:07:17,319 it to and that's the difference between 187 00:07:15,960 --> 00:07:19,280 these two actually because on the 188 00:07:17,319 --> 00:07:20,599 multi-tenant one with a many to many you 189 00:07:19,280 --> 00:07:23,120 actually have to save it differently 190 00:07:20,599 --> 00:07:24,840 because it can't exist you have it has 191 00:07:23,120 --> 00:07:27,520 to exist before you save it to the other 192 00:07:24,840 --> 00:07:29,520 object with the Min to mini table so 193 00:07:27,520 --> 00:07:32,360 that's slight difference between the two 194 00:07:29,520 --> 00:07:34,199 they're otherwise the same really um 195 00:07:32,360 --> 00:07:35,479 then we have obviously because we've 196 00:07:34,199 --> 00:07:36,840 made some classes we're going to have 197 00:07:35,479 --> 00:07:38,440 some detail views you know we're going 198 00:07:36,840 --> 00:07:40,840 to have to expose that data to our front 199 00:07:38,440 --> 00:07:43,840 end nothing fancy here you know I think 200 00:07:40,840 --> 00:07:45,159 everyone's seen a detail you before now 201 00:07:43,840 --> 00:07:46,919 the middleware is where it starts to get 202 00:07:45,159 --> 00:07:48,680 fun because we're going to actually have 203 00:07:46,919 --> 00:07:49,960 to keep track of the tenant as we run 204 00:07:48,680 --> 00:07:52,280 through the entire request response 205 00:07:49,960 --> 00:07:55,720 cycle the request has come in for a 206 00:07:52,280 --> 00:07:58,639 tenants data which tenant and do I want 207 00:07:55,720 --> 00:08:00,120 to try and modify every single call to 208 00:07:58,639 --> 00:08:02,440 pass it down the stack 209 00:08:00,120 --> 00:08:04,720 no so the only really good place to put 210 00:08:02,440 --> 00:08:06,879 that is a thread local which you'll see 211 00:08:04,720 --> 00:08:08,759 in a second because when we put it in a 212 00:08:06,879 --> 00:08:11,120 thread local we can actually get that 213 00:08:08,759 --> 00:08:13,479 tenant information wherever we need to 214 00:08:11,120 --> 00:08:13,479 access 215 00:08:14,240 --> 00:08:20,240 it and using it this way kind of gives 216 00:08:18,080 --> 00:08:23,479 us that escape hatch because we don't 217 00:08:20,240 --> 00:08:24,680 want to need lots of extra refactoring 218 00:08:23,479 --> 00:08:27,120 every time we change something about 219 00:08:24,680 --> 00:08:28,440 this that straightforward thread local 220 00:08:27,120 --> 00:08:31,599 just bypasses the 221 00:08:28,440 --> 00:08:32,839 complexity although when came time to 222 00:08:31,599 --> 00:08:36,000 actually get it working with 223 00:08:32,839 --> 00:08:39,519 async it became a pain because this this 224 00:08:36,000 --> 00:08:40,640 code never worked with async at all and 225 00:08:39,519 --> 00:08:42,959 as mentioned earlier it needed to 226 00:08:40,640 --> 00:08:44,880 support a couple of third party apps and 227 00:08:42,959 --> 00:08:46,200 then we have the duplicates here it had 228 00:08:44,880 --> 00:08:48,240 to be marked as a duplicate to stop my 229 00:08:46,200 --> 00:08:49,880 IDE complaining because it is 230 00:08:48,240 --> 00:08:51,959 functionally just a duplicate but 231 00:08:49,880 --> 00:08:54,320 because of how polymorphic works you 232 00:08:51,959 --> 00:08:57,080 need to actually subass from its model 233 00:08:54,320 --> 00:08:59,519 manager and create basically a duplicate 234 00:08:57,080 --> 00:09:02,440 for this kind of work it doesn't the way 235 00:08:59,519 --> 00:09:04,120 it does polymorphism is its core model 236 00:09:02,440 --> 00:09:05,800 manager behaviors so you kind of have to 237 00:09:04,120 --> 00:09:06,920 extend them and you can't really 238 00:09:05,800 --> 00:09:08,399 substitute that and kind of have a 239 00:09:06,920 --> 00:09:12,279 universal one so there's a whole 240 00:09:08,399 --> 00:09:13,800 duplicate copy also base model has to be 241 00:09:12,279 --> 00:09:16,720 duplicated and we've got the 242 00:09:13,800 --> 00:09:18,560 multi-tenant one as well and the actual 243 00:09:16,720 --> 00:09:21,440 multi- based model there's a lot of 244 00:09:18,560 --> 00:09:23,680 repetition in this kind of code but as 245 00:09:21,440 --> 00:09:26,320 you flesh it out it does all make a lot 246 00:09:23,680 --> 00:09:28,360 of sense and then we had the Jango rest 247 00:09:26,320 --> 00:09:30,440 framework support with their permissions 248 00:09:28,360 --> 00:09:31,920 framework serializers for the tenant 249 00:09:30,440 --> 00:09:33,640 data so that the front end can actually 250 00:09:31,920 --> 00:09:36,920 get that data it's all very 251 00:09:33,640 --> 00:09:39,560 straightforward business stuff and again 252 00:09:36,920 --> 00:09:41,920 permissions permissions permissions and 253 00:09:39,560 --> 00:09:45,040 another serializer and another 254 00:09:41,920 --> 00:09:46,760 serializer and we see the permissions 255 00:09:45,040 --> 00:09:48,880 are where it really becomes a key thing 256 00:09:46,760 --> 00:09:51,640 here because when you think about the 257 00:09:48,880 --> 00:09:54,920 kind of purpose of this functionality is 258 00:09:51,640 --> 00:09:56,000 to separate data between customers 259 00:09:54,920 --> 00:09:57,640 naturally you need to make sure that 260 00:09:56,000 --> 00:09:59,399 your permissions are structured that way 261 00:09:57,640 --> 00:10:01,720 because obviously the permission to 262 00:09:59,399 --> 00:10:03,800 access the data for one tenant is not 263 00:10:01,720 --> 00:10:05,399 necessarily going to be completely 264 00:10:03,800 --> 00:10:06,640 decoupled from the permission to access 265 00:10:05,399 --> 00:10:09,040 the data of another tenant because if 266 00:10:06,640 --> 00:10:11,040 you're say a manager in one office but 267 00:10:09,040 --> 00:10:12,640 you're only allowed access to read data 268 00:10:11,040 --> 00:10:14,000 for a different office that's going to 269 00:10:12,640 --> 00:10:16,279 be a different permission structure to 270 00:10:14,000 --> 00:10:17,920 say being a manager that owns all of 271 00:10:16,279 --> 00:10:20,800 them and having full access to 272 00:10:17,920 --> 00:10:22,160 everything so there's a bit of a complex 273 00:10:20,800 --> 00:10:23,360 relationship that needs to be handled in 274 00:10:22,160 --> 00:10:25,200 these permissions which is why that's 275 00:10:23,360 --> 00:10:28,600 not the whole of it it's actually this 276 00:10:25,200 --> 00:10:31,360 much so the permissions really kind of 277 00:10:28,600 --> 00:10:33,600 give an idea where the real core of this 278 00:10:31,360 --> 00:10:35,360 app's purpose is it it is designed to 279 00:10:33,600 --> 00:10:37,560 manage and control this the 280 00:10:35,360 --> 00:10:39,079 straightforward business logic of those 281 00:10:37,560 --> 00:10:41,480 previous ones really comes down to the 282 00:10:39,079 --> 00:10:43,600 nuts and bolts of how do I make sure 283 00:10:41,480 --> 00:10:45,440 that I'm handling the customer data the 284 00:10:43,600 --> 00:10:48,560 correct way for the users requesting 285 00:10:45,440 --> 00:10:50,000 stuff in the app and consequently when 286 00:10:48,560 --> 00:10:51,120 you actually have all that noisy code 287 00:10:50,000 --> 00:10:52,399 you kind of want to you want to make 288 00:10:51,120 --> 00:10:53,880 your life easier you have a lot of 289 00:10:52,399 --> 00:10:56,000 helpers for this kind of stuff you know 290 00:10:53,880 --> 00:10:57,800 things like a bypass mode because if 291 00:10:56,000 --> 00:10:59,720 you're running a management command you 292 00:10:57,800 --> 00:11:01,800 don't want all the queries in the entire 293 00:10:59,720 --> 00:11:03,800 thing complaining because you didn't 294 00:11:01,800 --> 00:11:06,360 give the management command a tenant you 295 00:11:03,800 --> 00:11:08,600 want to just have that code run on 296 00:11:06,360 --> 00:11:10,680 everything hence we start making little 297 00:11:08,600 --> 00:11:11,880 shortcuts here um there's actually a 298 00:11:10,680 --> 00:11:13,079 nice little thing there at the bottom 299 00:11:11,880 --> 00:11:14,839 there talking about Sentinels there's 300 00:11:13,079 --> 00:11:16,760 actually currently a Pepin proposal for 301 00:11:14,839 --> 00:11:18,600 adding Sentinels as a built-in Python 302 00:11:16,760 --> 00:11:20,320 language feature I think they're awesome 303 00:11:18,600 --> 00:11:22,519 it's kind of one of those little things 304 00:11:20,320 --> 00:11:24,320 you don't appreciate until you need it 305 00:11:22,519 --> 00:11:26,880 now in this particular case and enom 306 00:11:24,320 --> 00:11:28,600 would have done the job but enom weren't 307 00:11:26,880 --> 00:11:31,959 a language feature fully integrated at 308 00:11:28,600 --> 00:11:33,560 the time this was actually built so it's 309 00:11:31,959 --> 00:11:35,560 a case where Sentinels were the 310 00:11:33,560 --> 00:11:37,839 appropriate solution there 311 00:11:35,560 --> 00:11:39,560 now it's another talk for someone else 312 00:11:37,839 --> 00:11:42,240 to do but Sentinels are quite a nice 313 00:11:39,560 --> 00:11:43,639 feature um there are more tenant helpers 314 00:11:42,240 --> 00:11:45,839 you know things like requesting which 315 00:11:43,639 --> 00:11:47,880 tenant came in based on HTTP headers you 316 00:11:45,839 --> 00:11:50,360 know all the sort of standard SAS logic 317 00:11:47,880 --> 00:11:54,920 stuff it's you know the kind of thing 318 00:11:50,360 --> 00:11:56,760 you write lots of these for uh but once 319 00:11:54,920 --> 00:12:00,200 you're done writing it all we get to the 320 00:11:56,760 --> 00:12:03,519 testing and and this is where the uh the 321 00:12:00,200 --> 00:12:05,240 problems begin because management had a 322 00:12:03,519 --> 00:12:07,399 particular philosophy around this choice 323 00:12:05,240 --> 00:12:10,560 to make it reusable it's it's we put it 324 00:12:07,399 --> 00:12:14,360 to the side so that we can test it 325 00:12:10,560 --> 00:12:16,360 really well and I not kidding I actually 326 00:12:14,360 --> 00:12:18,800 did an entire talk about the stuff I 327 00:12:16,360 --> 00:12:21,199 learned to do the testing for this app 328 00:12:18,800 --> 00:12:24,079 because it was that extensive it was 329 00:12:21,199 --> 00:12:26,680 very extensive you know cross database 330 00:12:24,079 --> 00:12:30,120 testing you know we're running the local 331 00:12:26,680 --> 00:12:32,000 tests in sqlite but is it actually going 332 00:12:30,120 --> 00:12:35,160 to work the same when we run against 333 00:12:32,000 --> 00:12:37,760 postgress they wanted to make sure so we 334 00:12:35,160 --> 00:12:40,839 kept building tests I even ended up 335 00:12:37,760 --> 00:12:44,720 making a better hypothesis test because 336 00:12:40,839 --> 00:12:47,519 uh look. net.org is nice but you know 337 00:12:44,720 --> 00:12:50,440 what if we break paing on a do you know 338 00:12:47,519 --> 00:12:52,680 NL you know somehow someone manages to 339 00:12:50,440 --> 00:12:55,240 you know mess something up and break the 340 00:12:52,680 --> 00:12:57,079 tenant selection logic and trick our 341 00:12:55,240 --> 00:12:59,360 system no we can't have that have to 342 00:12:57,079 --> 00:13:01,199 test it properly yet more time time 343 00:12:59,360 --> 00:13:02,720 spent learning how to make this work and 344 00:13:01,199 --> 00:13:04,360 actually building this and getting this 345 00:13:02,720 --> 00:13:05,680 to actually do its job and I actually 346 00:13:04,360 --> 00:13:07,360 ended up turning it into a pull request 347 00:13:05,680 --> 00:13:08,839 and submitted it Upstream because it was 348 00:13:07,360 --> 00:13:11,880 that much you know work getting it all 349 00:13:08,839 --> 00:13:15,240 to run performant and again yet more 350 00:13:11,880 --> 00:13:17,519 time burnt testing now in the end there 351 00:13:15,240 --> 00:13:21,079 is a decent size test suite for this and 352 00:13:17,519 --> 00:13:23,079 it does all pass and it's pretty 353 00:13:21,079 --> 00:13:24,720 extensive coverage too there's a few 354 00:13:23,079 --> 00:13:26,399 places in there where you know I never 355 00:13:24,720 --> 00:13:29,120 could work out how to get it to do those 356 00:13:26,399 --> 00:13:31,639 last one or two lines but overall 357 00:13:29,120 --> 00:13:34,839 extremely high level of test coverage as 358 00:13:31,639 --> 00:13:38,199 mandated by management and that's kind 359 00:13:34,839 --> 00:13:38,199 of where the mistake really 360 00:13:41,920 --> 00:13:46,120 lies because management wanted to gold 361 00:13:45,120 --> 00:13:49,199 plate 362 00:13:46,120 --> 00:13:51,560 everything and um yeah gold plating 363 00:13:49,199 --> 00:13:53,560 everything is not necessarily a good 364 00:13:51,560 --> 00:13:55,440 idea 365 00:13:53,560 --> 00:13:56,920 um now if you're not familiar with the 366 00:13:55,440 --> 00:13:59,360 idea of gold plating something it's kind 367 00:13:56,920 --> 00:14:02,519 of the Monster oxygen-free Cable kind of 368 00:13:59,360 --> 00:14:04,399 a a notion it it may serve a purpose but 369 00:14:02,519 --> 00:14:07,519 it's probably pointless it it's a 370 00:14:04,399 --> 00:14:09,199 wasteful Endeavor it serves some level 371 00:14:07,519 --> 00:14:10,839 of use in the sense that a goldplated 372 00:14:09,199 --> 00:14:12,639 connector will wear out slightly 373 00:14:10,839 --> 00:14:14,800 differently and won't oxidize and it may 374 00:14:12,639 --> 00:14:16,360 have a purpose but you don't gold plate 375 00:14:14,800 --> 00:14:17,360 everything you gold plate the things 376 00:14:16,360 --> 00:14:20,560 that need to be 377 00:14:17,360 --> 00:14:24,399 goldplated but the the planning led to 378 00:14:20,560 --> 00:14:26,399 gold plating everything and that's the 379 00:14:24,399 --> 00:14:29,279 real context criticality in the middle 380 00:14:26,399 --> 00:14:31,720 of all of this that just like an 381 00:14:29,279 --> 00:14:34,199 abandoned subway station here this was 382 00:14:31,720 --> 00:14:36,240 built for a purpose but that purpose was 383 00:14:34,199 --> 00:14:38,279 never realized because the larger 384 00:14:36,240 --> 00:14:39,759 context in which it was built wasn't 385 00:14:38,279 --> 00:14:42,279 taken into 386 00:14:39,759 --> 00:14:44,040 consideration what ends up happening is 387 00:14:42,279 --> 00:14:46,399 that lots and lots of time is sunk 388 00:14:44,040 --> 00:14:49,519 building this reusable core logic 389 00:14:46,399 --> 00:14:51,920 testing it to the ends of the Earth and 390 00:14:49,519 --> 00:14:54,880 back but the rest of the project moves 391 00:14:51,920 --> 00:14:56,279 on the front end gets developed and 392 00:14:54,880 --> 00:14:58,440 management are looking at a front end 393 00:14:56,279 --> 00:15:00,959 that works completely but has no actual 394 00:14:58,440 --> 00:15:03,320 data behind it and the rest of the 395 00:15:00,959 --> 00:15:06,519 system hasn't caught up yet because this 396 00:15:03,320 --> 00:15:09,079 is still being built and tested which is 397 00:15:06,519 --> 00:15:11,040 very much a case of premature 398 00:15:09,079 --> 00:15:13,639 optimization this was prematurely 399 00:15:11,040 --> 00:15:15,040 optimized for a security posture grossly 400 00:15:13,639 --> 00:15:19,360 out of proportion for what it was 401 00:15:15,040 --> 00:15:21,440 needing to do and consequently it fell 402 00:15:19,360 --> 00:15:23,000 to this Maxim and this is a pretty 403 00:15:21,440 --> 00:15:24,759 common Trope you know there there's a 404 00:15:23,000 --> 00:15:27,720 reason that this Trope actually goes all 405 00:15:24,759 --> 00:15:29,880 the way back to Shakespeare because 406 00:15:27,720 --> 00:15:31,480 there is so many ways that you can trick 407 00:15:29,880 --> 00:15:33,240 yourself into thinking that you are on 408 00:15:31,480 --> 00:15:35,079 this right path you will be looking 409 00:15:33,240 --> 00:15:37,319 forward you will project yourself to be 410 00:15:35,079 --> 00:15:40,360 a year from now and think I will need 411 00:15:37,319 --> 00:15:42,160 this in a year it's smart to do it now 412 00:15:40,360 --> 00:15:43,759 but it's not actually smart to do it now 413 00:15:42,160 --> 00:15:45,839 if what you're trying to do is something 414 00:15:43,759 --> 00:15:47,279 in two months what matters in a year 415 00:15:45,839 --> 00:15:48,639 from now is going to be something you 416 00:15:47,279 --> 00:15:51,040 should be thinking about six months from 417 00:15:48,639 --> 00:15:53,319 now not now because if you're literally 418 00:15:51,040 --> 00:15:56,959 building from scratch a prototype like 419 00:15:53,319 --> 00:15:59,160 this was going that far down the line is 420 00:15:56,959 --> 00:16:00,800 what actually led to this never actually 421 00:15:59,160 --> 00:16:03,720 being used and this code being 422 00:16:00,800 --> 00:16:06,160 completely wasted because the end 423 00:16:03,720 --> 00:16:07,600 outcome of this was that it was all 424 00:16:06,160 --> 00:16:10,800 thrown in the 425 00:16:07,600 --> 00:16:12,680 bin and consequently all of the time 426 00:16:10,800 --> 00:16:14,839 spent making and testing this the couple 427 00:16:12,680 --> 00:16:17,480 of months solid spent building just this 428 00:16:14,839 --> 00:16:19,240 one piece of functionality and for the 429 00:16:17,480 --> 00:16:20,839 most part the time that was spent 430 00:16:19,240 --> 00:16:24,240 building the other functionality around 431 00:16:20,839 --> 00:16:26,720 it all just became pointless because at 432 00:16:24,240 --> 00:16:28,279 the end of the day management were 433 00:16:26,720 --> 00:16:31,279 unhappy with the performance of a 434 00:16:28,279 --> 00:16:34,079 critical part of of the app and this is 435 00:16:31,279 --> 00:16:36,399 why it was thrown in the bin because as 436 00:16:34,079 --> 00:16:37,759 the front end was developed it got to a 437 00:16:36,399 --> 00:16:40,800 point where it was fully functional they 438 00:16:37,759 --> 00:16:42,920 were happy with the complete design and 439 00:16:40,800 --> 00:16:45,680 with that design complete it became time 440 00:16:42,920 --> 00:16:47,759 to plug the back end in and Jango rest 441 00:16:45,680 --> 00:16:49,360 framework can make this work with MJS 442 00:16:47,759 --> 00:16:52,199 it's a model driven system you match the 443 00:16:49,360 --> 00:16:54,279 models up and the API just takes it over 444 00:16:52,199 --> 00:16:56,680 for you not a lot of extra logic 445 00:16:54,279 --> 00:16:58,360 required it's really nice like that so 446 00:16:56,680 --> 00:17:00,120 we get the front end ready management a 447 00:16:58,360 --> 00:17:01,360 happy play with it and going like when's 448 00:17:00,120 --> 00:17:02,399 it going to work for real when's it 449 00:17:01,360 --> 00:17:03,439 going to work for real when's it going 450 00:17:02,399 --> 00:17:05,400 to work for 451 00:17:03,439 --> 00:17:07,199 real but it's not going to work for real 452 00:17:05,400 --> 00:17:10,880 until we're done doing all this other 453 00:17:07,199 --> 00:17:12,360 stuff and even then we get to this end 454 00:17:10,880 --> 00:17:14,079 point where we've managed to do this 455 00:17:12,360 --> 00:17:17,199 we've delivered this it's taken longer 456 00:17:14,079 --> 00:17:19,720 than they think it should have and then 457 00:17:17,199 --> 00:17:21,400 we h a little bit of a snag because any 458 00:17:19,720 --> 00:17:23,280 kind of quick prototype built this way 459 00:17:21,400 --> 00:17:24,839 is going to run into little problems and 460 00:17:23,280 --> 00:17:27,039 one of those little problems was that 461 00:17:24,839 --> 00:17:28,319 there was a very important function in 462 00:17:27,039 --> 00:17:29,520 the middle of it that involved a very 463 00:17:28,319 --> 00:17:31,559 large list 464 00:17:29,520 --> 00:17:34,039 and by default the way it did that list 465 00:17:31,559 --> 00:17:36,520 update was sent one API request for 466 00:17:34,039 --> 00:17:38,480 every single item in this list and some 467 00:17:36,520 --> 00:17:39,960 of these lists were hundreds long which 468 00:17:38,480 --> 00:17:42,039 meant that the browser would bottleneck 469 00:17:39,960 --> 00:17:44,480 on the round trip because it hit the max 470 00:17:42,039 --> 00:17:47,799 queries and so consequently it would 471 00:17:44,480 --> 00:17:50,200 just sort of sit there and take far too 472 00:17:47,799 --> 00:17:52,720 long for management to be happy with and 473 00:17:50,200 --> 00:17:55,000 that became priority number one and so 474 00:17:52,720 --> 00:17:57,679 we dropped everything and started fixing 475 00:17:55,000 --> 00:18:00,159 this now at this point all of the work 476 00:17:57,679 --> 00:18:03,760 has been done the app is functional the 477 00:18:00,159 --> 00:18:06,679 only issue is a single page performance 478 00:18:03,760 --> 00:18:07,559 optimization but getting it sorted out 479 00:18:06,679 --> 00:18:08,640 making sure that we're doing it the 480 00:18:07,559 --> 00:18:10,520 right way checking that we haven't 481 00:18:08,640 --> 00:18:11,600 tripped ourselves up somewhere else and 482 00:18:10,520 --> 00:18:13,480 doing it a way that doesn't break 483 00:18:11,600 --> 00:18:15,039 something else because any kind of a 484 00:18:13,480 --> 00:18:16,200 crash project you take a few short cuts 485 00:18:15,039 --> 00:18:17,640 and you find that you actually do 486 00:18:16,200 --> 00:18:20,720 something later that breaks the thing 487 00:18:17,640 --> 00:18:22,840 you did weeks ago we have that point 488 00:18:20,720 --> 00:18:25,240 where we kind of looks like we're doing 489 00:18:22,840 --> 00:18:27,039 nothing and after a little while after 490 00:18:25,240 --> 00:18:28,320 about you know 2 3 weeks of doing 491 00:18:27,039 --> 00:18:30,760 nothing management are like this is 492 00:18:28,320 --> 00:18:30,760 clearly fa 493 00:18:31,360 --> 00:18:35,840 bin and the project eventually gets 494 00:18:34,039 --> 00:18:37,600 Rewritten in a completely different 495 00:18:35,840 --> 00:18:41,320 language another team that's how 496 00:18:37,600 --> 00:18:42,679 business works but amusingly enough in 497 00:18:41,320 --> 00:18:45,039 this particular case there was a bit of 498 00:18:42,679 --> 00:18:46,799 a salvage job that could be done later 499 00:18:45,039 --> 00:18:49,760 because eventually it came time to do 500 00:18:46,799 --> 00:18:51,679 some other Project work and the needs 501 00:18:49,760 --> 00:18:54,880 actually lined up quite well with the 502 00:18:51,679 --> 00:18:57,559 entire rest of what was built beyond the 503 00:18:54,880 --> 00:18:59,320 actual multi- tendency so what was able 504 00:18:57,559 --> 00:19:01,880 to be done was was possible to 505 00:18:59,320 --> 00:19:03,600 completely rip out the multi-tenancy and 506 00:19:01,880 --> 00:19:05,360 just use the skeleton of what was left 507 00:19:03,600 --> 00:19:08,000 behind from before to deliver this 508 00:19:05,360 --> 00:19:09,960 functionality faster and you know in a 509 00:19:08,000 --> 00:19:12,000 weird Twist of irony the fact that it 510 00:19:09,960 --> 00:19:14,720 was a reusable app made it easier to rip 511 00:19:12,000 --> 00:19:17,600 that out and use the rest of the 512 00:19:14,720 --> 00:19:20,240 project because it wasn't embedded into 513 00:19:17,600 --> 00:19:21,720 the entirety of the project so if it had 514 00:19:20,240 --> 00:19:24,320 been done the correct way and actually 515 00:19:21,720 --> 00:19:26,159 just built as part of the projects logic 516 00:19:24,320 --> 00:19:28,880 instead of in a reusable app it would 517 00:19:26,159 --> 00:19:30,960 have been harder to do that 518 00:19:28,880 --> 00:19:32,799 but overall the fact that it could be 519 00:19:30,960 --> 00:19:34,520 salvaged doesn't actually change the 520 00:19:32,799 --> 00:19:37,200 fact that all that time was 521 00:19:34,520 --> 00:19:39,840 wasted and given that this is a pretty 522 00:19:37,200 --> 00:19:41,080 broad sort of Journey there's plenty of 523 00:19:39,840 --> 00:19:43,400 time for questions for people who want 524 00:19:41,080 --> 00:19:45,559 to dive into the specific details of How 525 00:19:43,400 --> 00:19:45,559 It 526 00:19:50,600 --> 00:19:55,440 unfolded Fabulous uh I'm happy to run 527 00:19:53,760 --> 00:19:57,120 around and get the mic to people who 528 00:19:55,440 --> 00:19:58,400 would like to ask a question please 529 00:19:57,120 --> 00:20:00,640 phrase your question in the form of a 530 00:19:58,400 --> 00:20:00,640 question 531 00:20:01,039 --> 00:20:07,640 here we 532 00:20:02,480 --> 00:20:07,640 go what language was it Rew written in 533 00:20:09,480 --> 00:20:12,880 cop what 534 00:20:14,760 --> 00:20:20,760 here great talk and what was unique 535 00:20:19,120 --> 00:20:23,559 about that management in wanting to go 536 00:20:20,760 --> 00:20:25,960 plate everything it it was a security 537 00:20:23,559 --> 00:20:29,159 concern and and and not not a completely 538 00:20:25,960 --> 00:20:31,480 unreasonable one just uh the the 539 00:20:29,159 --> 00:20:34,039 mismatch between the technical 540 00:20:31,480 --> 00:20:35,400 understanding of the potential risk 541 00:20:34,039 --> 00:20:37,799 because there was a bit of an insurance 542 00:20:35,400 --> 00:20:40,760 industry angle on some of this stuff 543 00:20:37,799 --> 00:20:42,720 there there was a a desire to be up to 544 00:20:40,760 --> 00:20:45,360 Snuff as far as an insurance company 545 00:20:42,720 --> 00:20:48,720 would want to see so so there was a bit 546 00:20:45,360 --> 00:20:51,120 of a bias towards needing far more 547 00:20:48,720 --> 00:20:54,440 guarantees and security coverage than 548 00:20:51,120 --> 00:20:54,440 they really needed in a 549 00:20:55,840 --> 00:21:00,480 prototype I'm sure somewhere on the 550 00:20:58,080 --> 00:21:02,720 project team someone spotted that this 551 00:21:00,480 --> 00:21:06,400 was going to be a train wreck early 552 00:21:02,720 --> 00:21:08,919 on what did the project team do to share 553 00:21:06,400 --> 00:21:11,520 that message and why was that message 554 00:21:08,919 --> 00:21:12,640 not received the the the project team 555 00:21:11,520 --> 00:21:15,240 was two 556 00:21:12,640 --> 00:21:20,240 people doing two different 557 00:21:15,240 --> 00:21:20,240 hes so no no one saw it 558 00:21:22,840 --> 00:21:27,880 coming 559 00:21:25,120 --> 00:21:30,880 here I'm got to invoke that word do you 560 00:21:27,880 --> 00:21:32,200 think this is a good uh argument for 561 00:21:30,880 --> 00:21:35,440 Agile 562 00:21:32,200 --> 00:21:37,480 development honestly yes because it 563 00:21:35,440 --> 00:21:39,279 would have been easier to recognize that 564 00:21:37,480 --> 00:21:41,120 the mismatch was occurring had there 565 00:21:39,279 --> 00:21:43,360 been regular check-ins like that instead 566 00:21:41,120 --> 00:21:45,679 of a more overarching project Milestone 567 00:21:43,360 --> 00:21:45,679 based 568 00:21:53,600 --> 00:22:00,120 approach is everyone 569 00:21:57,159 --> 00:22:03,960 okay everyone still has their jobs and 570 00:22:00,120 --> 00:22:07,600 uh you know no one's lost any work from 571 00:22:03,960 --> 00:22:09,919 it that is a great question particularly 572 00:22:07,600 --> 00:22:09,919 in this 573 00:22:10,360 --> 00:22:15,559 track uh what would you do differently 574 00:22:12,679 --> 00:22:17,120 now if you to do well I would definitely 575 00:22:15,559 --> 00:22:19,279 have Incorporated it into the actual 576 00:22:17,120 --> 00:22:20,880 project as opposed to a reusable app 577 00:22:19,279 --> 00:22:23,400 because if this had just been part of 578 00:22:20,880 --> 00:22:25,039 the project itself the integration to 579 00:22:23,400 --> 00:22:27,240 make it work with all the functionality 580 00:22:25,039 --> 00:22:29,360 was required would have been a much more 581 00:22:27,240 --> 00:22:31,360 straightforward process evolving along 582 00:22:29,360 --> 00:22:33,320 with the rest of the functionality 583 00:22:31,360 --> 00:22:35,720 instead of having to be built with all 584 00:22:33,320 --> 00:22:38,000 the extra hypotheticals attached to it 585 00:22:35,720 --> 00:22:40,840 because as as a reusable app there was a 586 00:22:38,000 --> 00:22:43,440 lot of sort of reusable app mindset 587 00:22:40,840 --> 00:22:46,720 involved uh many of those helpers were 588 00:22:43,440 --> 00:22:49,039 only used in the test Suite because when 589 00:22:46,720 --> 00:22:50,360 it was built the thought was H I don't 590 00:22:49,039 --> 00:22:52,279 know if I'm going to need this later but 591 00:22:50,360 --> 00:22:55,320 I'm here building this now I should 592 00:22:52,279 --> 00:22:57,240 build this now because it's reusable I'm 593 00:22:55,320 --> 00:22:59,640 going to make sure it just covers all my 594 00:22:57,240 --> 00:23:01,799 bases and that's leads to scope creep in 595 00:22:59,640 --> 00:23:01,799 that 596 00:23:04,559 --> 00:23:09,799 sense um uh I think uh we we are also 597 00:23:07,679 --> 00:23:13,120 embarking the same Journey you know you 598 00:23:09,799 --> 00:23:16,679 just mentioned but um uh what do you 599 00:23:13,120 --> 00:23:20,159 suggest you know how uh how not to 600 00:23:16,679 --> 00:23:22,200 fail ah the question of the day um yeah 601 00:23:20,159 --> 00:23:25,200 no in in terms of you know trying not to 602 00:23:22,200 --> 00:23:28,000 fail the lesson out of this is is to be 603 00:23:25,200 --> 00:23:30,120 mindful of that context because the the 604 00:23:28,000 --> 00:23:32,679 context that it was built in was where 605 00:23:30,120 --> 00:23:34,159 the real mismatch occurred if if the 606 00:23:32,679 --> 00:23:36,000 context had been appropriate and the 607 00:23:34,159 --> 00:23:38,000 goal was to use this in a lot of other 608 00:23:36,000 --> 00:23:39,279 applications in a larger organization 609 00:23:38,000 --> 00:23:41,840 this approach may have been perfectly 610 00:23:39,279 --> 00:23:43,440 sensible but that wasn't the context the 611 00:23:41,840 --> 00:23:46,600 context was it was being built for a 612 00:23:43,440 --> 00:23:48,760 single specific Django project that was 613 00:23:46,600 --> 00:23:50,919 going to be used as a single Django 614 00:23:48,760 --> 00:23:53,360 project in a SAS context it it didn't 615 00:23:50,919 --> 00:23:55,799 need this kind of reusable thinking and 616 00:23:53,360 --> 00:23:58,799 that context mismatch is what led to the 617 00:23:55,799 --> 00:23:58,799 failure 618 00:24:02,000 --> 00:24:04,960 we have another one over 619 00:24:05,320 --> 00:24:11,480 here uh presumably there are like 620 00:24:08,720 --> 00:24:13,720 multi-tenancy uh libraries already in 621 00:24:11,480 --> 00:24:16,679 Django uh did you explore those why 622 00:24:13,720 --> 00:24:18,720 weren't they up to stuff a lot of those 623 00:24:16,679 --> 00:24:20,640 a lot of the existing ones tend to do 624 00:24:18,720 --> 00:24:22,720 schema based isolation or multi- 625 00:24:20,640 --> 00:24:25,640 database switching because those are the 626 00:24:22,720 --> 00:24:29,399 kind of easiest ones to share um in 627 00:24:25,640 --> 00:24:32,880 particular for this one uh this is 628 00:24:29,399 --> 00:24:35,600 uh heavily improved from a very very 629 00:24:32,880 --> 00:24:36,840 minimal prototype I found out there 630 00:24:35,600 --> 00:24:41,200 which is part of the reason why the 631 00:24:36,840 --> 00:24:43,840 license is all squirly but the the core 632 00:24:41,200 --> 00:24:45,880 of it being that kind of extra rigor 633 00:24:43,840 --> 00:24:48,720 required to do this kind of everything 634 00:24:45,880 --> 00:24:51,039 lives in the one schema tends to lead to 635 00:24:48,720 --> 00:24:53,320 people not building it as a reusable app 636 00:24:51,039 --> 00:24:54,960 which back to the last question there is 637 00:24:53,320 --> 00:24:56,520 that if you were doing a project like 638 00:24:54,960 --> 00:25:00,760 that you normally make it part of your 639 00:24:56,520 --> 00:25:02,520 project not built as a reusable piece so 640 00:25:00,760 --> 00:25:04,320 for this specific case no actually there 641 00:25:02,520 --> 00:25:06,880 wasn't 642 00:25:04,320 --> 00:25:08,279 any okay I'll go here and then here and 643 00:25:06,880 --> 00:25:11,399 then 644 00:25:08,279 --> 00:25:13,720 here thanks it seems to me the main 645 00:25:11,399 --> 00:25:16,200 takeaway of your talk in the project was 646 00:25:13,720 --> 00:25:18,120 the the B you covered very briefly about 647 00:25:16,200 --> 00:25:20,760 management getting impatient with fixing 648 00:25:18,120 --> 00:25:24,720 a problem that took a bit too long like 649 00:25:20,760 --> 00:25:27,600 what what went on there in terms of 650 00:25:24,720 --> 00:25:30,240 communicating you know this is fixable 651 00:25:27,600 --> 00:25:32,159 it'll take a bit more more time you know 652 00:25:30,240 --> 00:25:35,520 this I don't know I mean like all the 653 00:25:32,159 --> 00:25:37,640 other stuff is is clearly useful but 654 00:25:35,520 --> 00:25:40,279 it's if that's where the project failed 655 00:25:37,640 --> 00:25:42,000 well you're not wrong um there there I'm 656 00:25:40,279 --> 00:25:43,480 I'm kind of tactically attempting to 657 00:25:42,000 --> 00:25:46,480 change the names to protect the innocent 658 00:25:43,480 --> 00:25:50,000 so to speak um but 659 00:25:46,480 --> 00:25:53,720 the the more broad detail on that is 660 00:25:50,000 --> 00:25:55,960 that the time that took from management 661 00:25:53,720 --> 00:25:58,840 being happy with the Prototype of dummy 662 00:25:55,960 --> 00:26:00,919 data to delivery of a real system that 663 00:25:58,840 --> 00:26:02,559 they could actually touch and save data 664 00:26:00,919 --> 00:26:05,960 to and begin trying to run through the 665 00:26:02,559 --> 00:26:08,960 cycles with was about 2 months so it was 666 00:26:05,960 --> 00:26:10,559 about two months of them staring at the 667 00:26:08,960 --> 00:26:12,360 thing that they were completely happy 668 00:26:10,559 --> 00:26:15,360 with but just had completely fake data 669 00:26:12,360 --> 00:26:17,399 in it and actually going to use it 670 00:26:15,360 --> 00:26:19,080 during which time visually for a 671 00:26:17,399 --> 00:26:20,640 non-technical management trying to 672 00:26:19,080 --> 00:26:23,039 design something based on their 673 00:26:20,640 --> 00:26:25,279 understanding of their own business they 674 00:26:23,039 --> 00:26:27,200 sort of perceived a standstill while 675 00:26:25,279 --> 00:26:29,640 work was being done behind the scenes in 676 00:26:27,200 --> 00:26:32,880 a sense this being done front end design 677 00:26:29,640 --> 00:26:35,159 first backend plugged in afterwards 678 00:26:32,880 --> 00:26:37,720 while a feature of emberjs that made 679 00:26:35,159 --> 00:26:40,080 that work well kind of also contributes 680 00:26:37,720 --> 00:26:42,799 to the management project delivery 681 00:26:40,080 --> 00:26:44,559 mismatch that kind of culminated in that 682 00:26:42,799 --> 00:26:46,880 final point of look we've waited this 683 00:26:44,559 --> 00:26:50,279 long now you hit another 684 00:26:46,880 --> 00:26:52,840 snag uh you can only string that along 685 00:26:50,279 --> 00:26:53,679 so so far before they start to decide 686 00:26:52,840 --> 00:26:56,320 you know what we're going to cut our 687 00:26:53,679 --> 00:26:56,320 losses on this 688 00:26:56,600 --> 00:27:00,240 one okay we 689 00:27:00,679 --> 00:27:05,840 great talk um do you have any specific 690 00:27:03,480 --> 00:27:08,840 suggestions on how to talk to management 691 00:27:05,840 --> 00:27:11,559 to avoid a situation like this when you 692 00:27:08,840 --> 00:27:13,880 see a context mismatch and they don't 693 00:27:11,559 --> 00:27:16,200 especially if they're um they don't have 694 00:27:13,880 --> 00:27:18,159 technical background 695 00:27:16,200 --> 00:27:20,559 well I suppose that's the thing I've 696 00:27:18,159 --> 00:27:22,440 kind of taken from this myself is is 697 00:27:20,559 --> 00:27:25,080 trying to be more mindful of the context 698 00:27:22,440 --> 00:27:27,080 and just to apply that regular sort of 699 00:27:25,080 --> 00:27:29,000 talk to management skill set that you 700 00:27:27,080 --> 00:27:32,080 know I have work as an independent 701 00:27:29,000 --> 00:27:34,279 developer but the in in this specific 702 00:27:32,080 --> 00:27:35,720 case having not recognized the context 703 00:27:34,279 --> 00:27:37,559 mismatch there wasn't really an 704 00:27:35,720 --> 00:27:40,679 opportunity for me to bring that up 705 00:27:37,559 --> 00:27:43,279 because I hadn't seen the problem 706 00:27:40,679 --> 00:27:44,840 yet but the regular skill set of if if 707 00:27:43,279 --> 00:27:46,159 you do see a problem like that you 708 00:27:44,840 --> 00:27:47,840 should just bring it up to the 709 00:27:46,159 --> 00:27:50,120 management you know to the best of your 710 00:27:47,840 --> 00:27:51,679 ability it's the soft skills component 711 00:27:50,120 --> 00:27:54,200 of of learning to work in this kind of 712 00:27:51,679 --> 00:27:56,000 an industry if you have that kind of 713 00:27:54,200 --> 00:27:56,840 role where you have an ability to speak 714 00:27:56,000 --> 00:27:58,600 to 715 00:27:56,840 --> 00:28:01,600 management that's that's part of the 716 00:27:58,600 --> 00:28:01,600 skill set you need to have to do 717 00:28:01,799 --> 00:28:05,559 it okay I think we had one more question 718 00:28:04,480 --> 00:28:08,840 which is I think we're going to have to 719 00:28:05,559 --> 00:28:10,320 call it there here we go I don't know 720 00:28:08,840 --> 00:28:12,600 we've got a hiveel over here but I was 721 00:28:10,320 --> 00:28:14,159 thinking along the same path and I guess 722 00:28:12,600 --> 00:28:15,640 sort of Management's mentioned a few 723 00:28:14,159 --> 00:28:17,640 times I know there's some developers 724 00:28:15,640 --> 00:28:19,919 involved as well and I guess I was kind 725 00:28:17,640 --> 00:28:21,240 of curious about like where they were 726 00:28:19,919 --> 00:28:23,000 you in-house developers where you're 727 00:28:21,240 --> 00:28:25,320 external I'm sort of trying to work out 728 00:28:23,000 --> 00:28:27,399 the motivations of both sides here so 729 00:28:25,320 --> 00:28:29,120 certainly when you know like wasn't made 730 00:28:27,399 --> 00:28:31,000 clear to manager that you know this is 731 00:28:29,120 --> 00:28:33,679 is a front end there's a lot going the 732 00:28:31,000 --> 00:28:36,240 background like those kind of project 733 00:28:33,679 --> 00:28:37,320 planning aspects as well which I know um 734 00:28:36,240 --> 00:28:38,960 I sort of get the feeling everyone in 735 00:28:37,320 --> 00:28:41,760 this room is very bright and can develop 736 00:28:38,960 --> 00:28:43,200 things but actually getting it to 737 00:28:41,760 --> 00:28:45,240 getting people who don't understand what 738 00:28:43,200 --> 00:28:47,039 we do on board and making sure they 739 00:28:45,240 --> 00:28:49,000 understand the timelines and where the 740 00:28:47,039 --> 00:28:51,720 importance is and you know were the 741 00:28:49,000 --> 00:28:53,000 developers at the time even if we regret 742 00:28:51,720 --> 00:28:54,519 it now was it sort of just in the 743 00:28:53,000 --> 00:28:56,360 mindset of just we're going to make the 744 00:28:54,519 --> 00:28:58,120 thing they asked us to or was it sort of 745 00:28:56,360 --> 00:28:59,679 in the mindset of sort of trying to 746 00:28:58,120 --> 00:29:01,679 solve that problem if you if you get 747 00:28:59,679 --> 00:29:04,000 what I mean there was a little bit of 748 00:29:01,679 --> 00:29:05,960 both um you know I I I was the senior 749 00:29:04,000 --> 00:29:08,720 developer on this one um there was an 750 00:29:05,960 --> 00:29:10,880 inhouse Junior uh in that particular 751 00:29:08,720 --> 00:29:13,320 situation I was being brought in as more 752 00:29:10,880 --> 00:29:14,960 experienced uh to sort of steer things 753 00:29:13,320 --> 00:29:18,799 and do other work for other projects had 754 00:29:14,960 --> 00:29:21,600 going um the the overall cycle was 755 00:29:18,799 --> 00:29:22,760 actually kind of broken in those two 756 00:29:21,600 --> 00:29:25,159 halves there was the development of the 757 00:29:22,760 --> 00:29:26,960 front end discovering the users needs 758 00:29:25,159 --> 00:29:28,519 and actually actively communicating with 759 00:29:26,960 --> 00:29:30,720 them to try and find out what they 760 00:29:28,519 --> 00:29:33,480 wanted and to build the best app 761 00:29:30,720 --> 00:29:35,840 possible for the job they needed it done 762 00:29:33,480 --> 00:29:37,880 but where the mismatch came in and and 763 00:29:35,840 --> 00:29:39,360 sort of what that you know I think 764 00:29:37,880 --> 00:29:41,799 you're getting at there is is that there 765 00:29:39,360 --> 00:29:43,960 was that mismatch in terms of whether or 766 00:29:41,799 --> 00:29:46,399 not it was fully understood by them what 767 00:29:43,960 --> 00:29:49,159 was going on in the second half and and 768 00:29:46,399 --> 00:29:51,440 while that was outlined as part of the 769 00:29:49,159 --> 00:29:53,200 planning the amount of time that passed 770 00:29:51,440 --> 00:29:55,600 in between those two steps may have led 771 00:29:53,200 --> 00:29:58,919 to some sort of misconception creeping 772 00:29:55,600 --> 00:30:01,720 in that wasn't identified until 773 00:29:58,919 --> 00:30:03,960 at the end of the actual outcome they 774 00:30:01,720 --> 00:30:06,120 decided that you know their perception 775 00:30:03,960 --> 00:30:08,559 had shifted significantly from what it 776 00:30:06,120 --> 00:30:11,279 was originally in that very interactive 777 00:30:08,559 --> 00:30:12,799 phase for them and that that's sort of 778 00:30:11,279 --> 00:30:15,559 more of a social capital kind of a 779 00:30:12,799 --> 00:30:17,279 problem in terms of trust in the actual 780 00:30:15,559 --> 00:30:20,200 relationship you know you deliver it 781 00:30:17,279 --> 00:30:21,640 very very quickly trust builds they 782 00:30:20,200 --> 00:30:23,120 start to see that things aren't being 783 00:30:21,640 --> 00:30:25,120 delivered at the same rate there's going 784 00:30:23,120 --> 00:30:26,679 to be a gradual erosion of the trust in 785 00:30:25,120 --> 00:30:29,080 terms of that management communication 786 00:30:26,679 --> 00:30:30,440 flow and and you have to be mindful of 787 00:30:29,080 --> 00:30:32,559 that in terms of you know that 788 00:30:30,440 --> 00:30:34,080 communication pathway and making sure 789 00:30:32,559 --> 00:30:36,519 that you know they are actually on board 790 00:30:34,080 --> 00:30:38,120 and do understand but once there starts 791 00:30:36,519 --> 00:30:40,159 to be that sort of misconception and 792 00:30:38,120 --> 00:30:42,200 that slow gradual loss of the Social 793 00:30:40,159 --> 00:30:43,640 Capital they will begin to question 794 00:30:42,200 --> 00:30:46,519 whether or not you're actually giving 795 00:30:43,640 --> 00:30:48,279 them and feeding them Al line and you 796 00:30:46,519 --> 00:30:51,519 don't really have the thing and at that 797 00:30:48,279 --> 00:30:51,519 point it's all going to fall apart 798 00:30:53,120 --> 00:30:59,440 anyway all righty that was quite a 799 00:30:56,399 --> 00:31:03,240 story very interesting thank you we have 800 00:30:59,440 --> 00:31:03,240 a special gift for