Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Real World Dashboard

Ben Sheldon
May 13, 2014
140

Real World Dashboard

When Backbone.js stops being idiomatic, and starts being real.

Ben Sheldon

May 13, 2014
Tweet

Transcript

  1. • Transparent: The consequences of change should be obvious in

    the code that is changing and in distant code that relies upon it. • Reasonable: The cost of any change should be proportional to the benefits the change achieves • Usable: Existing code should be usable in new and unexpected contexts • Exemplary: The code itself should encourage those who change it to perpetuate these qualities. T.R.U.E. CODE http://www.poodr.com/
  2. “Fuck design patterns” “I don’t know. I just copied it.”

    “Is it bad, or is it you didn't write it?” CLASSIC
  3. The code itself should encourage those who change it to

    perpetuate these qualities. EXEMPLARY CODE http://randycoulman.com/blog/2013/04/09/exemplary-code/
  4. VS

  5. ANTI-DESIGN Design: making guesses about unknown requirements and writing speculative

    code in an attempt to preemptively meet them. Design == Over-Design PRO-DESIGN Design: the current arrangement of an application’s code Act of Design: using one’s knowledge of the consequences of various code arrangement techniques to solve the current problem in a way that accommodates the next (as yet undefined) change. “These disputes are not about core beliefs, they merely reflect a communication gap.” http://www.sandimetz.com/blog/2012/07/05/how-shall-we-define-design/
  6. REDUCE DUPLICATION apiUser: (path='', data={}, method='GET', callback) -> start =

    new Date().getTime() # … param munging omitted parameters = user: app.settings.user path: path unless _.isUndefined(data) or _.isFunction(data) parameters.data = data log.debug 'REQ', "#{method} user/#{path}", parameters request(method, '/pp.php') .send(parameters) .end((res) => log.debug 'RES', "#{method} user/#{path}", res # If the response has a 5xx status code, record this. if res.status >= 500 recordAPIFail(method, path, data, res) # Record how long the api request took. app.util.apiTiming(path, new Date().getTime() - start) if res.status >= 400 if res.body? error = res.body else error = res.status else error = null if _.isFunction callback return callback error, res.body, res ) makeSiteApiFunction: (siteId) -> return (path='', data={}, method = 'GET') -> start = new Date().getTime() # … param munging omitted parameters = site: siteId path: path unless _.isUndefined(data) or _.isFunction(data) parameters.data = data log.debug 'REQ', "#{method} site/#{path}", parameters request(method, '/pp.php') .send(parameters) .end((res) => log.debug 'RES', "#{method} site/#{path}", res # Record how long the api request took. app.util.apiTiming(path, new Date().getTime() - start) # If the response has a 5xx status code, record this. if res.status >= 500 recordAPIFail(method, path, data, res) if res.status >= 400 error = res.status else error = null if _.isFunction callback return callback error, res.body, res ) memoized different param slightly different error checking code same code, different order
  7. MODULARITY window.app.util.analyticsTrack() window.app.util.userGet() window.app.util.userSet() window.app.util.makeSiteApi() window.app.util.apiUser() window.app.util.sendGraphite() window.app.util.getGravatar() window.app.util.apiTiming() window.app.util.getAccentColor()

    window.app.util.featureEnabled() window.app.util.parseSize() window.app.util.uuidFromEmail() window.app.util.createCSVDownload() window.app.util.isOnebox() window.app.util.validateEmail() window.app.util.pardotTrack()
  8. Do (not “must”) Don’t (not “can’t”) Dependencies are injected or

    required() Access window.app deep in methods Export singletons Attach to window.app view.render() is idempotent View.render() appends to html API calls happen on models/collections Make API calls in View Use templates Concat/$.append html strings in Views Inject primitive values into templates Inject fat objects/models into templates Assign @options.property to @property in #initialize Access @options.property deep in other methods initialize() doesn't have side effects such as auto- render Make api calls in initialize or call render() Views should listen to model state and re-render Use jQuery to modify specific elements on events DASHBOARD EPIC