This approach proposes that an class instance be placed in urls.py; the instance has a !__call!__() method, and when that method is invoked, it takes a shallow copy of the instance defined in urls.py, and returns the result of invoking the request method (e.g., GET()). This achieves thread safety by ensuring that every request is given a clean instance on the view class to work on.

64

This approach proposes that an class instance be placed in urls.py; the instance has a `__call__()` method, and when that method is invoked, it takes a shallow copy of the instance defined in urls.py, and returns the result of invoking the request method (e.g., GET()). This achieves thread safety by ensuring that every request is given a clean instance on the view class to work on.

65

65

66

66

No special handling is required in !UrlResolver -- the class instance is a callable, so it appears just like an existing view function.

67

67

68

68

Arguments against:

69

* The "copy on !__call!__()" approach is a little messy. Normal Python idiom wouldn't lead users to expect that !__call!__() would cause a copy to be created.

70

* The abstraction of the copy-on-call can leak in surprising ways. Some users will try to set up state using an !__init!__ method (common practice). If any of the state they attach to self in !__init!__ is mutable (list, dict, object, etc) and they mutate it in the view, this will fail (but not immediately, or in obvious ways).

69

* The "copy on `__call__()`" approach is a little messy. Normal Python idiom wouldn't lead users to expect that `__call__()` would cause a copy to be created.

70

* The abstraction of the copy-on-call can leak in surprising ways. Some users will try to set up state using an `__init__` method (common practice). If any of the state they attach to self in `__init__` is mutable (list, dict, object, etc) and they mutate it in the view, this will fail (but not immediately, or in obvious ways).