contents

preface

acknowledgments

about this book

about the author

about the cover illustration

1 To the streets

1.1 What matters in the streets

1.2 Who’s a street coder?

1.3 Great street coders

Questioning

Results-driven

High-throughput

Embracing complexity and ambiguity

1.4 The problems of modern software development

Too many technologies

Paragliding on paradigms

The black boxes of technology

Underestimating overhead

Not my job

Menial is genial

1.5 What this book isn’t

1.6 Themes

2 Practical theory

2.1 A crash course on algorithms

Big-O better be good

2.2 Inside data structures

String

Array

List

Linked list

Queue

Dictionary

HashSet

Stack

Call stack

2.3 What’s the hype on types?

Being strong on the type

Proof of validity

Don’t framework hard, framework smart

Types over typos

To be nullable or non-nullable

Better performance for free

Reference types vs. value types

3 Useful anti-patterns

3.1 If it ain’t broke, break it

Facing code rigidity

Move fast, break things

Respecting boundaries

Isolating common functionality

Example web page

Leave no debt behind

3.2 Write it from scratch

Erase and rewrite

3.3 Fix it, even if it ain’t broke

Race toward the future

Cleanliness is next to codeliness

3.4 Do repeat yourself

Reuse or copy?

3.5 Invent it here

3.6 Don’t use inheritance

3.7 Don’t use classes

Enum is yum!

Structs rock!

3.8 Write bad code

Don’t use If/Else

Use goto

3.9 Don’t write code comments

Choose great names

Leverage functions

4 Tasty testing

4.1 Types of tests

Manual testing

Automated tests

Living dangerously: Testing in production

Choosing the right testing methodology

4.2 How to stop worrying and love the tests

4.3 Don’t use TDD or other acronyms

4.4 Write tests for your own good

4.5 Deciding what to test

Respect boundaries

Code coverage

4.6 Don’t write tests

Don’t write code

Don’t write all the tests

4.7 Let the compiler test your code

Eliminate null checks

Eliminate range checks

Eliminate valid value checks

4.8 Naming tests

5 Rewarding refactoring

5.1 Why do we refactor?

5.2 Architectural changes

Identify the components

Estimate the work and the risk

The prestige

Refactor to make refactoring easier

The final stretch

5.3 Reliable refactoring

5.4 When not to refactor

6 Security by scrutiny

6.1 Beyond hackers

6.2 Threat modeling

Pocket-sized threat models

6.3 Write secure web apps

Design with security in mind

Usefulness of security by obscurity

Don’t implement your own security

SQL injection attacks

Cross-site scripting

Cross-site request forgery

6.4 Draw the first flood

Don’t use captcha

Captcha alternatives

Don’t implement a cache

6.5 Storing secrets

Keeping secrets in source code

7 Opinionated optimization

7.1 Solve the right problem

Simple benchmarking

Performance vs. responsiveness

7.2 Anatomy of sluggishness

7.3 Start from the top

Nested loops

String-oriented programming

Evaluating 2b || !2b

7.4 Breaking the bottle at the neck

Don’t pack data

Shop local

Keep dependent works separated

Be predictable

SIMD

7.5 1s and 0s of I/O

Make I/O faster

Make I/O non-blocking

The archaic ways

Modern async/await

Gotchas of async I/O

7.6 If all else fails, cache

8 Palatable scalability

8.1 Don’t use locks

Double-checked locking

8.2 Embrace inconsistency

The dreaded NOLOCK

8.3 Don’t cache database connections

In the form of an ORM

8.4 Don’t use threads

The gotchas of async code

MULTITHREADING with async

8.5 Respect the monolith

9 Living with bugs

9.1 Don’t fix bugs

9.2 The error terror

The bare truth of exceptions

Don’t catch exceptions

Exception resiliency

Resiliency without transactions

Exceptions vs. errors

9.3 Don’t debug

printf() debugging

Dump diving

Advanced rubber-duck debugging

index

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.118.110.109