Ouch, my fault. I deleted the wrong bindings. 

> On Jul 24, 2017, at 1:58 PM, Philip McGrath <[email protected]> wrote:
> 
> Sorry for the crossed emails. If I understand what's happening correctly, the 
> code you sent only blames the "deserializing" module because it shaddows 
> `serialize` and `deserialize` to mean `values`, so the instance is never 
> actually deserialized or serialized and `deserialize-info:adder-v0` is never 
> consulted. If I remove the `local` block, the error is displayed in terms of 
> `+`.
> 
> #lang racket
> 
> (module server racket
>   (require racket/serialize)
>   
>   (provide (contract-out
>             [adder (-> natural-number/c (-> natural-number/c 
> natural-number/c))]))
>   
>   (struct adder (base)
>     #:property prop:procedure
>     (λ (this x) (+ (adder-base this) x))
>     #:property prop:serializable
>     (make-serialize-info (λ (this) (vector (adder-base this)))
>                          #'deserialize-info:adder-v0
>                          #f
>                          (or (current-load-relative-directory)
>                              (current-directory))))
>   
>   (define deserialize-info:adder-v0
>     (make-deserialize-info adder (λ () (error 'adder "can't have cycles"))))
>   
>   (module+ deserialize-info
>     (provide deserialize-info:adder-v0)))
>   
> (require (submod "." server) racket/serialize)
> 
> (define x (serialize (adder 5)))
> (displayln x)
> (define f (deserialize x))
> (f 'not-a-number) 
> 
> -Philip
> 
> On Mon, Jul 24, 2017 at 12:50 PM, Philip McGrath <[email protected]> 
> wrote:
> It occurs to me that one approach is to use the low-level `contract` form 
> directly. It gives better blame than `define/contract`, at least. The program:
> 
> #lang racket
> 
> (module server racket
>   (require racket/serialize)
>   
>   (provide (contract-out
>             [adder (-> natural-number/c (-> natural-number/c 
> natural-number/c))]))
>   
>   (struct adder (base)
>     #:property prop:procedure
>     (λ (this x) (+ (adder-base this) x))
>     #:property prop:serializable
>     (make-serialize-info (λ (this) (vector (adder-base this)))
>                          #'deserialize-info:adder-v0
>                          #f
>                          (or (current-load-relative-directory)
>                              (current-directory))))
>   
>   (define deserialize-info:adder-v0
>     (make-deserialize-info
>      (λ (base)
>        (define inst (adder base))
>        (contract (-> natural-number/c natural-number/c)
>                  inst
>                  '(definition adder)
>                  `(deserialization ,inst)
>                  (object-name adder)
>                  #f))
>      (λ () (error 'adder "can't have cycles"))))
>   
>   (module+ deserialize-info
>     (provide deserialize-info:adder-v0)))
>   
> (require (submod "." server) racket/serialize)
> 
> ((deserialize (serialize (adder 5))) 'not-a-number)
> 
> reports the error:
> 
> adder: contract violation
>   expected: natural-number/c
>   given: 'not-a-number
>   in: the 1st argument of
>       (-> natural-number/c natural-number/c)
>   contract from: (definition adder)
>   blaming: (deserialization #<procedure:adder>)
>    (assuming the contract is correct)
> 
> 
> -Philip
> 
> On Mon, Jul 24, 2017 at 12:35 PM, Philip McGrath <[email protected]> 
> wrote:
> That is precisely the contract violation I'd like to see reported, but, 
> without the shadowing of serialize and deserialize, the error is reported in 
> terms of `+`. (And, if it wasn't clear, I do intend to actually read and 
> write the serialized instance.)
> 
> I (think) I understand why deserialization strips the contract from the 
> instance: the contract is added at the module boundary using the 
> chaperone/impersonator infrastructure, and deserialization uses the 
> unprotected form of `adder` passed to `make-deserialize-info` within the 
> server module. 
> 
> What I don't understand is how to give `make-deserialize-info` a function 
> that (1) has a contract where (2) fulfilling the range part of the contract 
> becomes the deserializing module's obligation — if such a thing is possible. 
> Aside from attempts with `define/contract` (which as I now understand 
> achieved point 1 but not point 2), I've also tried putting the definition of 
> `deserialize-info:adder-v0` in a different module, so that its version of 
> `adder` has a contract, but then the binding isn't seen by 
> `make-serialize-info`.
> 
> -Philip
> 
> On Mon, Jul 24, 2017 at 7:30 AM, Matthias Felleisen <[email protected]> 
> wrote:
> 
>> On Jul 23, 2017, at 10:50 PM, Philip McGrath <[email protected]> 
>> wrote:
>> 
>> If I'm following correctly, I think that's what I was trying to do, but I'm 
>> unclear how to give `make-deserialize-info` a variant of `make-adder` that 
>> has a contract. The initial example with `define/contract` was the closest 
>> I've come: it at least reported violations in terms of `make-adder` rather 
>> than `+`, but (as I now understand) it blamed the `server` module for all 
>> violations.
>> 
>> -Philip
>> 
>> On Sun, Jul 23, 2017 at 9:27 PM, Matthew Flatt <[email protected]> wrote:
>> The original example had an explicit deserializer:
>> 
>> At Sun, 23 Jul 2017 19:54:43 -0500, Philip McGrath wrote:
>> >   (define deserialize-info:adder-v0
>> >     (make-deserialize-info make-adder
>> >                            (λ () (error 'adder
>> >                                         "can't have cycles"))))
>> 
>> You're constructing the deserializer with `make-adder` --- the variant
>> from inside the `server` module, so it doesn't have a contract.
>> 
>> I think this is where you want to draw a new boundary by giving
>> `make-deserialize-info` a variant of `make-adder` that has a contract.
> 
> 
> 
> Don’t you just want this: 
> 
> #lang racket
> 
> (module server racket
>   (require racket/serialize)
>   
>   (provide (contract-out
>             [adder (-> natural-number/c (-> natural-number/c 
> natural-number/c))]))
>   
>   (struct adder (base)
>     #:property prop:procedure
>     (λ (this x) (+ (adder-base this) x))
>     #:property prop:serializable
>     (make-serialize-info (λ (this) (vector (adder-base this)))
>                          #'deserialize-info:adder-v0
>                          #f
>                          (or (current-load-relative-directory)
>                              (current-directory))))
>   
>   (define deserialize-info:adder-v0
>     (make-deserialize-info adder (λ () (error 'adder "can't have cycles"))))
>   
>   (module+ deserialize-info
>     (provide deserialize-info:adder-v0)))
>   
> (require (submod "." server) racket/serialize)
> 
> (local ((define serialize values)
>         (define deserialize values))
>   (define x (serialize (adder 5)))
>   (define f (deserialize x))
>   (f 'not-a-number))
> 
> 
> 
> 
> 

-- 
You received this message because you are subscribed to the Google Groups 
"Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to